/*
 * Copyright (C) 2019 The Android Open Source Project
 *
 * Licensed 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 com.googlesource.gerrit.plugins.auditsl4j.logsource;

import static com.google.gerrit.server.AuditEvent.UNKNOWN_SESSION_ID;

import com.google.gerrit.server.AccessPath;
import com.google.gerrit.server.audit.HttpAuditEvent;
import com.googlesource.gerrit.plugins.auditsl4j.AuditUser;
import com.googlesource.gerrit.plugins.auditsl4j.LoggerAudit;
import com.googlesource.gerrit.plugins.auditsl4j.TransformableAuditLogType;
import com.googlesource.gerrit.plugins.auditsl4j.TransformableLog;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.Optional;
import java.util.regex.Matcher;
import java.util.regex.Pattern;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

public class HTTPLog implements TransformableLog {
  private static final Logger log = LoggerFactory.getLogger(HTTPLog.class);
  private String ip;
  private String user;
  private String method;
  private String timestamp;
  private String resource;
  private String protocol;
  private Integer status;
  private String contentLength;
  private String referrer;
  private String userAgent;

  public HTTPLog(
      String ip,
      String user,
      String timestamp,
      String method,
      String resource,
      String protocol,
      Integer status,
      String contentLength,
      String referrer,
      String userAgent) {
    this.ip = ip;
    this.user = user;
    this.method = method;
    this.timestamp = timestamp;
    this.resource = resource;
    this.protocol = protocol;
    this.status = status;
    this.contentLength = contentLength;
    this.referrer = referrer;
    this.userAgent = userAgent;
  }

  public static Optional<HTTPLog> createFromLog(String line) {
    // HTTP log example:
    // 104.32.164.100 - - [24/Jan/2019:00:00:03 +0000] "GET /plugins/events-log/ HTTP/1.1" 404 9 -
    // "Apache-HttpClient/4.5.3 (Java/1.8.0_191)"
    Matcher a =
        Pattern.compile(
                "^(?<ip>.*?)\\s-\\s(?<user>.*?)\\s\\["
                    + "(?<timestamp>.*?)\\]\\s\""
                    + "(?<method>\\w+)\\s(?<resource>.*?)\\s(?<protocol>.*?)\"\\s"
                    + "(?<status>\\d+)\\s(?<contentLength>\\d+|-)\\s(?<referrer>.*?)\\s(?<userAgent>.*?)$")
            .matcher(line);
    if (a.matches()) {
      try {
        return Optional.of(
            new HTTPLog(
                a.group("ip"),
                a.group("user"),
                a.group("timestamp"),
                a.group("method"),
                a.group("resource"),
                a.group("protocol"),
                Integer.parseInt(a.group("status")),
                a.group("contentLength"),
                a.group("referrer"),
                a.group("userAgent")));
      } catch (Exception e) {
        log.error("Something wrong while parsing line: " + line);
      }
    } else {
      log.error("Can't extract any info from line: " + line);
    }
    return Optional.empty();
  }

  private AuditUser getAuditUser() {
    AuditUser au = new AuditUser();
    au.setUserName(this.user);
    au.setAccessPath(getAccessPath());
    return au;
  }

  private AccessPath getAccessPath() {
    Matcher a = Pattern.compile("^\"git.*?").matcher(this.userAgent);
    return a.matches() ? AccessPath.GIT : AccessPath.REST_API;
  }

  public Optional<Long> getWhen() {
    SimpleDateFormat format = new SimpleDateFormat("dd/MMM/yyyy:hh:mm:ss Z");
    try {
      return Optional.of(format.parse(this.timestamp).getTime());
    } catch (ParseException pe) {
      log.error(
          "Can't parse timestamp: '" + this.timestamp + "'. Error message: " + pe.getMessage());
    }
    return Optional.empty();
  }

  public Optional<String> toAuditLog(LoggerAudit loggerAudit) {
    return getWhen()
        .map(
            when ->
                new HttpAuditEvent(
                    UNKNOWN_SESSION_ID,
                    this.getAuditUser(),
                    this.resource,
                    when,
                    null,
                    this.method,
                    null,
                    this.status,
                    null))
        .map(
            httpAuditEvent -> {
              AuditUser au = getAuditUser();
              if (au.getAccessPath() == AccessPath.REST_API) {
                return loggerAudit.getAuditString(
                    httpAuditEvent, TransformableAuditLogType.ExtendedHttpAuditEvent);
              } else {
                return loggerAudit.getAuditString(
                    httpAuditEvent, TransformableAuditLogType.HttpAuditEvent);
              }
            });
  }

  public static String logFilenameBase() {
    return "httpd_log";
  }

  public String getIp() {
    return ip;
  }

  public String getUser() {
    return user;
  }

  public String getMethod() {
    return method;
  }

  public String getTimestamp() {
    return timestamp;
  }

  public String getResource() {
    return resource;
  }

  public String getProtocol() {
    return protocol;
  }

  public Integer getStatus() {
    return status;
  }

  public String getContentLength() {
    return contentLength;
  }

  public String getReferrer() {
    return referrer;
  }

  public String getUserAgent() {
    return userAgent;
  }
}
