package ru.yandex.qe.http.aspects.log;

import java.util.ArrayList;
import java.util.List;

import com.google.common.base.Function;
import org.apache.http.Header;
import org.apache.http.HttpEntity;
import org.apache.http.HttpEntityEnclosingRequest;
import org.apache.http.HttpRequest;
import org.apache.http.HttpResponse;
import org.apache.http.message.BasicHeader;

import ru.yandex.qe.logging.security.PrivateHeaderSecurityGuard;

/**
 * Established by terry
 * on 16.03.14.
 */
public class LogHttpUtils {

    public static Function<HttpRequest, String> requestUrlHeadersEntityLogFunction(List<PrivateHeaderSecurityGuard> privateHeaderSecurityGuards) {
        return request -> {
            final StringBuilder stringBuilder = new StringBuilder(request.getRequestLine().toString());
            final Header[] headers = request.getAllHeaders();
            final List<Header> securedHeaders = new ArrayList<>(headers.length);
            for (Header header : headers) {
                String headerValue = header.getValue();
                for (PrivateHeaderSecurityGuard privateHeaderSecurityGuard : privateHeaderSecurityGuards) {
                    headerValue = privateHeaderSecurityGuard.secure(header.getName(), headerValue);
                }
                securedHeaders.add(new BasicHeader(header.getName(), headerValue));
            }
            stringBuilder.append(" ").append(securedHeaders);

            if (request instanceof HttpEntityEnclosingRequest) {
                final HttpEntityEnclosingRequest httpEntityEnclosingRequest = (HttpEntityEnclosingRequest) request;
                final HttpEntity entity = httpEntityEnclosingRequest.getEntity();
                stringBuilder.append(", entity: ");
                if (entity != null) {
                    stringBuilder.append("length = ").append(entity.getContentLength()).append(", ")
                            .append(entity.getContentType()).append(", ")
                            .append(entity.getContentEncoding()).append(", repeatable = ")
                            .append(entity.isRepeatable()).append(", chunked = ")
                            .append(entity.isChunked()).append(", streaming = ")
                            .append(entity.isStreaming());
                } else {
                    stringBuilder.append("null");
                }
            }
            return stringBuilder.toString();
        };
    }

    public static Function<HttpResponse, String> responseUrlHeadersEntityLogFunction(List<PrivateHeaderSecurityGuard> privateHeaderSecurityGuards) {
        return response -> {
            final StringBuilder stringBuilder = new StringBuilder(response.getStatusLine().toString());
            final Header[] headers = response.getAllHeaders();
            final List<Header> securedHeaders = new ArrayList<>(headers.length);
            for (Header header : headers) {
                String headerValue = header.getValue();
                for (PrivateHeaderSecurityGuard privateHeaderSecurityGuard : privateHeaderSecurityGuards) {
                    headerValue = privateHeaderSecurityGuard.secure(header.getName(), headerValue);
                }
                securedHeaders.add(new BasicHeader(header.getName(), headerValue));
            }
            stringBuilder.append(" ").append(securedHeaders);

            final HttpEntity entity = response.getEntity();
            stringBuilder.append(", entity: ");
            if (entity != null) {
                stringBuilder.append("length = ").append(entity.getContentLength()).append(", ")
                        .append(entity.getContentType()).append(", ")
                        .append(entity.getContentEncoding()).append(", repeatable = ")
                        .append(entity.isRepeatable()).append(", chunked = ")
                        .append(entity.isChunked()).append(", streaming = ")
                        .append(entity.isStreaming());
            } else {
                stringBuilder.append("null");
            }
            return stringBuilder.toString();
        };
    }
}
