package com.falydoor.limesurveyrest;

import com.falydoor.limesurveyrest.dto.*;
import com.falydoor.limesurveyrest.exception.LimesurveyRestException;
import com.google.gson.*;
import org.apache.http.HttpResponse;
import org.apache.http.client.methods.HttpPost;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClientBuilder;
import org.apache.http.util.EntityUtils;

import java.io.IOException;
import java.time.ZonedDateTime;
import java.util.Comparator;
import java.util.stream.Stream;
import java.util.stream.StreamSupport;

public class LimesurveyRest {

    private String url;

    private String user;

    private String password;

    private int keyTimeout = 7200;

    private String key = "";

    private ZonedDateTime keyExpiration = ZonedDateTime.now();

    public LimesurveyRest(String url, String user, String password) {
        this.url = url;
        this.user = user;
        this.password = password;
    }

    public void setKeyTimeout(int timeout) {
        keyTimeout = timeout;
    }

    public JsonElement callApi(LimesurveyApiBody limesurveyApiBody) throws LimesurveyRestException {
        try (CloseableHttpClient client = HttpClientBuilder.create().build()) {
            HttpPost post = new HttpPost(url);
            post.setHeader("Content-type", "application/json");
            post.setEntity(new StringEntity(new Gson().toJson(limesurveyApiBody)));
            HttpResponse response = client.execute(post);
            if (response.getStatusLine().getStatusCode() == 200) {
                String result = EntityUtils.toString(response.getEntity());
                return new JsonParser().parse(result).getAsJsonObject().get("result");
            } else {
                throw new LimesurveyRestException("Expecting status code 200, got " + response.getStatusLine().getStatusCode() + " instead");
            }
        } catch (IOException e) {
            throw new LimesurveyRestException("Exception while calling API : " + e.getMessage(), e);
        }
    }

    public String getSessionKey() throws LimesurveyRestException {
        // Use the saved key if isn't expired
        if (!key.isEmpty() && ZonedDateTime.now().isBefore(keyExpiration)) {
            return key;
        }

        // Get session key and save it with an expiration set to 1 minute before the expiration date
        LimesurveyApiBody.LimesurveyApiParams params = new LimesurveyApiBody.LimesurveyApiParams();
        params.setUsername(user);
        params.setPassword(password);
        JsonElement result = callApi(new LimesurveyApiBody("get_session_key", params));
        key = result.getAsString();
        keyExpiration = ZonedDateTime.now().plusSeconds(keyTimeout - 60);

        return key;
    }

}

@@ -2081,32 +2081,1100 @@
        %7D%0A    %7D%0A%0A
+    public boolean isSurveyActive(int surveyId) throws LimesurveyRestException %7B%0A        LimesurveyApiBody.LimesurveyApiParams params = getParamsWithKey(surveyId);%0A        JsonArray surveySettings = new JsonArray();%0A        surveySettings.add(new JsonPrimitive(%22active%22));%0A        params.setSurveySettings(surveySettings);%0A%0A        return %22Y%22.equals(callApi(new LimesurveyApiBody(%22get_survey_properties%22, params)).getAsJsonObject().get(%22active%22).getAsString());%0A    %7D%0A%0A    public boolean isSurveyExists(int surveyId) throws LimesurveyRestException %7B%0A        return getSurveys().anyMatch(survey -%3E survey.getId() == surveyId);%0A    %7D%0A%0A    public Stream%3CLimesurveySurvey%3E getActiveSurveys() throws LimesurveyRestException %7B%0A        return getSurveys().filter(LimesurveySurvey::isActive);%0A    %7D%0A%0A    public Stream%3CLimesurveySurvey%3E getSurveys() throws LimesurveyRestException %7B%0A        return StreamSupport.stream(callApi(new LimesurveyApiBody(%22list_surveys%22, getParamsWithKey())).getAsJsonArray().spliterator(), false)%0A                .map(LimesurveySurvey::new);%0A    %7D%0A%0A
     public Strin
@@ -3881,10 +3881,546 @@
 %0A    %7D%0A%0A
+    private LimesurveyApiBody.LimesurveyApiParams getParamsWithKey(int surveyId) throws LimesurveyRestException %7B%0A        LimesurveyApiBody.LimesurveyApiParams params = getParamsWithKey();%0A        params.setSurveyId(surveyId);%0A        return params;%0A    %7D%0A%0A    private LimesurveyApiBody.LimesurveyApiParams getParamsWithKey() throws LimesurveyRestException %7B%0A        LimesurveyApiBody.LimesurveyApiParams params = new LimesurveyApiBody.LimesurveyApiParams();%0A        params.setSessionKey(getSessionKey());%0A        return params;%0A    %7D%0A%0A
 %7D%0A

Add isSurveyActive, isSurveyExists, getActiveSurveys and getSurveys methods