/**
 * Licensed to the Apache Software Foundation (ASF) under one
 * or more contributor license agreements. See the NOTICE file
 * distributed with this work for additional information
 * regarding copyright ownership. The ASF licenses this file
 * to you under the Apache License, Version 2.0 (the
 * "License"); you may not use this file except in compliance
 * with the License. You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing,
 * software distributed under the License is distributed on an
 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
 * KIND, either express or implied. See the License for the
 * specific language governing permissions and limitations
 * under the License.
 */

package org.apache.cxf.fediz.jetty9;

import java.time.Instant;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;

import javax.security.auth.Subject;
import javax.servlet.ServletRequest;

import org.apache.cxf.fediz.core.config.FedizContext;
import org.apache.cxf.fediz.core.exception.ProcessingException;
import org.apache.cxf.fediz.core.processor.FedizProcessor;
import org.apache.cxf.fediz.core.processor.FedizProcessorFactory;
import org.apache.cxf.fediz.core.processor.FedizRequest;
import org.apache.cxf.fediz.core.processor.FedizResponse;
import org.eclipse.jetty.security.IdentityService;
import org.eclipse.jetty.security.LoginService;
import org.eclipse.jetty.server.UserIdentity;
import org.eclipse.jetty.util.component.AbstractLifeCycle;
import org.eclipse.jetty.util.log.Log;
import org.eclipse.jetty.util.log.Logger;

public class FederationLoginService extends AbstractLifeCycle implements LoginService {
    private static final Logger LOG = Log.getLogger(FederationLoginService.class);

    protected IdentityService identityService = new FederationIdentityService();
    protected String name;


    public FederationLoginService() {
    }

    public FederationLoginService(String name) {
        this.name = name;
    }

    @Override
    public String getName() {
        return name;
    }

    public void setName(String name) {
        if (isRunning()) {
            throw new IllegalStateException("Running");
        }

        this.name = name;
    }

    @Override
    protected void doStart() throws Exception {
        LOG.debug("doStart");
        super.doStart();
    }

    /**
     * username will be null since the credentials will contain all the relevant info
     */
    public UserIdentity login(String username, Object credentials, FedizContext config) {

        try {
            FedizResponse wfRes = null;
            FedizRequest wfReq = (FedizRequest)credentials;

            if (LOG.isDebugEnabled()) {
                LOG.debug("Process SignIn request");
                LOG.debug("token=\n" + wfReq.getResponseToken());
            }

            FedizProcessor wfProc =
                FedizProcessorFactory.newFedizProcessor(config.getProtocol());
            try {
                wfRes = wfProc.processRequest(wfReq, config);
            } catch (ProcessingException ex) {
                LOG.warn("Federation processing failed: " + ex.getMessage());
                return null;
            }


            // Validate the AudienceRestriction in Security Token (e.g. SAML)
            // against the configured list of audienceURIs
            if (wfRes.getAudience() != null) {
                List<String> audienceURIs = config.getAudienceUris();
                boolean validAudience = false;
                for (String a : audienceURIs) {
                    if (wfRes.getAudience().startsWith(a)) {
                        validAudience = true;
                        break;
                    }
                }

                if (!validAudience) {
                    LOG.warn("Token AudienceRestriction [" + wfRes.getAudience()
                             + "] doesn't match with specified list of URIs.");
                    return null;
                }
            }

            // Add "Authenticated" role
            List<String> roles = wfRes.getRoles();
            if (roles == null || roles.isEmpty()) {
                roles = Collections.singletonList("Authenticated");
            } else if (config.isAddAuthenticatedRole()) {
                roles = new ArrayList<>(roles);
                roles.add("Authenticated");
            }

            FederationUserPrincipal user = new FederationUserPrincipal(wfRes.getUsername(), wfRes);

            Subject subject = new Subject();
            subject.getPrincipals().add(user);

            String[] aRoles = new String[roles.size()];
            roles.toArray(aRoles);

            return identityService.newUserIdentity(subject, user, aRoles);

        } catch (Exception ex) {
            LOG.warn(ex);
        }

        return null;
    }

    public boolean validate(UserIdentity user) {
        try {
            FederationUserIdentity fui = (FederationUserIdentity)user;
            return fui.getExpiryDate().isAfter(Instant.now());
        } catch (ClassCastException ex) {
            LOG.warn("UserIdentity must be instance of FederationUserIdentity");
            throw new IllegalStateException("UserIdentity must be instance of FederationUserIdentity");
        }
    }

    @Override
    public IdentityService getIdentityService() {
        return identityService;
    }

    @Override
    public void setIdentityService(IdentityService service) {
        identityService = service;
    }

    public void logout(UserIdentity user) {

    }

    @Override
    public UserIdentity login(String username, Object credentials, ServletRequest arg2) {
        return null;
    }

}
