@Override
  public String getConfigFormSnippet(
      ConnectorManager connectorManager,
      String connectorType,
      String connectorName,
      Locale locale) {
    Element xml;

    Map<String, String> paramsMap = new HashMap<String, String>();
    paramsMap.put(ServletUtil.QUERY_PARAM_LANG, locale.getLanguage());

    if (connectorName == null) {
      // New connector
      paramsMap.put(ServletUtil.XMLTAG_CONNECTOR_TYPE, connectorType);
      xml = ConnectorManagerRequestUtils.sendGet(connectorManager, "/getConfigForm", paramsMap);
    } else {
      // Existing connector
      paramsMap.put(ServletUtil.XMLTAG_CONNECTOR_NAME, connectorName);
      xml =
          ConnectorManagerRequestUtils.sendGet(
              connectorManager, "/getConnectorConfigToEdit", paramsMap);
    }

    Element formSnippet =
        xml.element(ServletUtil.XMLTAG_CONFIGURE_RESPONSE).element(ServletUtil.XMLTAG_FORM_SNIPPET);
    CDATA cdata = (CDATA) formSnippet.node(0);
    String configFormSnippetText = cdata.getStringValue();

    return configFormSnippetText;
  }
  @Override
  public Schedule getSchedule(ConnectorManager connectorManager, String connectorName) {
    Schedule schedule;

    Map<String, String> paramsMap = new HashMap<String, String>();
    paramsMap.put(ServletUtil.XMLTAG_CONNECTOR_NAME, connectorName);
    try {
      Element xml =
          ConnectorManagerRequestUtils.sendGet(connectorManager, "/getSchedule", paramsMap);
      Element connectorStatusElement = xml.element(ServletUtil.XMLTAG_CONNECTOR_STATUS);
      Element connectorScheduleElement =
          connectorStatusElement.element(ServletUtil.XMLTAG_CONNECTOR_SCHEDULES);

      String scheduleTxt = connectorScheduleElement.getTextTrim();
      if (!StringUtils.isEmpty(scheduleTxt)) {
        schedule = new Schedule(scheduleTxt);
      } else {
        schedule = null;
      }
    } catch (Exception e) {
      LOGGER.log(Level.SEVERE, "Error while trying to get schedule", e);
      schedule = null;
    }
    return schedule;
  }
 @SuppressWarnings("unchecked")
 @Override
 public List<String> getConnectorInstanceNames(
     ConnectorManager connectorManager, String collectionName) {
   List<String> connectorInstanceNames = new ArrayList<String>();
   RecordCollectionServices collectionServices =
       ConstellioSpringUtils.getRecordCollectionServices();
   RecordCollection collection = collectionServices.get(collectionName);
   if (collection != null) {
     Element xml =
         ConnectorManagerRequestUtils.sendGet(connectorManager, "/getConnectorInstanceList", null);
     // ConnectorInstances / ConnectorInstance / ConnectorName
     if (xml.element(ServletUtil.XMLTAG_CONNECTOR_INSTANCES) != null) {
       List<Element> connectorIntanceElements =
           xml.element(ServletUtil.XMLTAG_CONNECTOR_INSTANCES)
               .elements(ServletUtil.XMLTAG_CONNECTOR_INSTANCE);
       for (Iterator<Element> it = connectorIntanceElements.iterator(); it.hasNext(); ) {
         Element connectorInstanceElement = (Element) it.next();
         Element connectorInstanceNameElement =
             connectorInstanceElement.element(ServletUtil.XMLTAG_CONNECTOR_NAME);
         String connectorInstanceName = connectorInstanceNameElement.getTextTrim();
         if (collection.getConnectorInstance(connectorInstanceName) != null) {
           connectorInstanceNames.add(connectorInstanceName);
         }
       }
     }
   }
   return connectorInstanceNames;
 }
 @Override
 public void disableConnector(ConnectorManager connectorManager, String connectorName) {
   Schedule schedule = getSchedule(connectorManager, connectorName);
   if (schedule != null) {
     schedule.setDisabled(true);
     setSchedule(connectorManager, connectorName, schedule);
     Map<String, String> paramsMap = new HashMap<String, String>();
     paramsMap.put(ServletUtil.XMLTAG_CONNECTOR_NAME, connectorName);
     ConnectorManagerRequestUtils.sendGet(connectorManager, "/stopConnector", paramsMap);
   }
 }
 @Override
 public void restartTraversal(ConnectorManager connectorManager, String connectorName) {
   Schedule schedule = getSchedule(connectorManager, connectorName);
   if (schedule != null && schedule.isDisabled()) {
     schedule.setDisabled(false);
     setSchedule(connectorManager, connectorName, schedule);
   }
   Map<String, String> paramsMap = new HashMap<String, String>();
   paramsMap.put(ServletUtil.XMLTAG_CONNECTOR_NAME, connectorName);
   ConnectorManagerRequestUtils.sendGet(connectorManager, "/restartConnectorTraversal", paramsMap);
 }
 @Override
 public String getConnectorType(ConnectorManager connectorManager, String connectorName) {
   Map<String, String> paramsMap = new HashMap<String, String>();
   paramsMap.put(ServletUtil.XMLTAG_CONNECTOR_NAME, connectorName.toLowerCase());
   Element xml =
       ConnectorManagerRequestUtils.sendGet(connectorManager, "/getConnectorStatus", paramsMap);
   Element connectorTypeElement =
       xml.element(ServletUtil.XMLTAG_CONNECTOR_STATUS).element(ServletUtil.XMLTAG_CONNECTOR_TYPE);
   String connectoryType = connectorTypeElement.getTextTrim();
   return connectoryType;
 }
  @Override
  public void removeConnector(ConnectorManager connectorManager, String connectorName) {
    String connectorType = getConnectorType(connectorManager, connectorName);

    Map<String, String> paramsMap = new HashMap<String, String>();
    paramsMap.put(ServletUtil.XMLTAG_CONNECTOR_NAME, connectorName);
    ConnectorManagerRequestUtils.sendGet(connectorManager, "/removeConnector", paramsMap);

    BackupServices backupServices = ConstellioSpringUtils.getBackupServices();
    if (backupServices.hasConfigBackup(connectorName, connectorType)) {
      backupServices.deleteConfigBackup(connectorName, connectorType);
    }
  }
 @SuppressWarnings("unchecked")
 @Override
 public List<String> getConnectorTypes(ConnectorManager connectorManager) {
   // On utilise le connectorManager par défaut.
   Element xml = ConnectorManagerRequestUtils.sendGet(connectorManager, "/getConnectorList", null);
   List<Element> connectorTypeElements =
       xml.element(ServletUtil.XMLTAG_CONNECTOR_TYPES).elements(ServletUtil.XMLTAG_CONNECTOR_TYPE);
   List<String> connectorTypes = new ArrayList<String>();
   for (Iterator<Element> it = connectorTypeElements.iterator(); it.hasNext(); ) {
     Element connectorTypeElement = (Element) it.next();
     connectorTypes.add(connectorTypeElement.getTextTrim());
   }
   return connectorTypes;
 }
 @SuppressWarnings("unchecked")
 @Override
 public Map<String, String> getConfig(ConnectorManager connectorManager, String connectorName) {
   Map<String, String> connectorConfigMap = new HashMap<String, String>();
   Map<String, String> paramsMap = new HashMap<String, String>();
   paramsMap.put(ServletUtil.XMLTAG_CONNECTOR_NAME, connectorName);
   Element xml =
       ConnectorManagerRequestUtils.sendGet(connectorManager, "/getConnectorConfig", paramsMap);
   List<Element> connectorConfigElements =
       xml.element(ServletUtil.XMLTAG_CONFIGURE_RESPONSE).elements(ServletUtil.XMLTAG_PARAMETERS);
   for (Element connectorConfigElement : connectorConfigElements) {
     String name = connectorConfigElement.attributeValue("name");
     String value = connectorConfigElement.attributeValue("value");
     connectorConfigMap.put(name, value);
   }
   return connectorConfigMap;
 }
  @Override
  public void setSchedule(
      ConnectorManager connectorManager, String connectorName, Schedule schedule) {
    Document document = DocumentHelper.createDocument();
    Element root = document.addElement(ServletUtil.XMLTAG_CONNECTOR_SCHEDULES);
    root.addElement(ServletUtil.XMLTAG_CONNECTOR_NAME).addText(connectorName);
    if (schedule.isDisabled()) {
      root.addElement(ServletUtil.XMLTAG_DISABLED).addText(Boolean.toString(schedule.isDisabled()));
    }
    root.addElement(ServletUtil.XMLTAG_LOAD).addText(Integer.toString(schedule.getLoad()));
    root.addElement(ServletUtil.XMLTAG_DELAY)
        .addText(Integer.toString(schedule.getRetryDelayMillis()));
    root.addElement(ServletUtil.XMLTAG_TIME_INTERVALS).addText(schedule.getTimeIntervalsAsString());
    ConnectorManagerRequestUtils.sendPost(connectorManager, "/setSchedule", document);

    String connectorType = getConnectorType(connectorManager, connectorName);
    BackupServices backupServices = ConstellioSpringUtils.getBackupServices();
    backupServices.backupConfig(connectorName, connectorType);
  }
  private Element setConnectorConfig(
      ConnectorManager connectorManager,
      String connectorName,
      String connectorType,
      Map<String, String[]> requestParams,
      boolean update,
      Locale locale) {
    Document document = DocumentHelper.createDocument();
    Element root = document.addElement(ServletUtil.XMLTAG_CONNECTOR_CONFIG);

    root.addElement(ServletUtil.QUERY_PARAM_LANG).addText(locale.getLanguage());
    root.addElement(ServletUtil.XMLTAG_CONNECTOR_NAME).addText(connectorName);
    root.addElement(ServletUtil.XMLTAG_CONNECTOR_TYPE).addText(connectorType);
    root.addElement(ServletUtil.XMLTAG_UPDATE_CONNECTOR).addText(Boolean.toString(update));

    for (String paramName : requestParams.keySet()) {
      if (!paramName.startsWith("wicket:")) {
        String[] paramValues = requestParams.get(paramName);
        for (String paramValue : paramValues) {
          Element paramElement = root.addElement(ServletUtil.XMLTAG_PARAMETERS);
          paramElement.addAttribute("name", paramName);
          paramElement.addAttribute("value", paramValue);
        }
      }
    }

    Element response =
        ConnectorManagerRequestUtils.sendPost(connectorManager, "/setConnectorConfig", document);
    Element statusIdElement = response.element(ServletUtil.XMLTAG_STATUSID);
    if (statusIdElement != null) {
      String statusId = statusIdElement.getTextTrim();
      if (!statusId.equals("" + ConnectorMessageCode.SUCCESS)) {
        return response;
      } else {
        BackupServices backupServices = ConstellioSpringUtils.getBackupServices();
        backupServices.backupConfig(connectorName, connectorType);
        return null;
      }
    } else {
      return null;
    }
  }
  @SuppressWarnings("unchecked")
  @Override
  public List<Record> authorizeByConnector(
      List<Record> records,
      Collection<UserCredentials> userCredentialsList,
      ConnectorManager connectorManager) {
    List<Record> authorizedRecords = new ArrayList<Record>();

    Document document = DocumentHelper.createDocument();
    Element root = document.addElement(ServletUtil.XMLTAG_AUTHZ_QUERY);
    Element connectorQueryElement = root.addElement(ServletUtil.XMLTAG_CONNECTOR_QUERY);

    Map<ConnectorInstance, UserCredentials> credentialsMap =
        new HashMap<ConnectorInstance, UserCredentials>();
    Set<ConnectorInstance> connectorsWithoutCredentials = new HashSet<ConnectorInstance>();
    Map<String, Record> recordsByURLMap = new HashMap<String, Record>();
    boolean recordToValidate = false;
    for (Record record : records) {
      // Use to accelerate the matching between response urls and actual entities
      recordsByURLMap.put(record.getUrl(), record);
      ConnectorInstance connectorInstance = record.getConnectorInstance();
      UserCredentials connectorCredentials = credentialsMap.get(connectorInstance);
      if (connectorCredentials == null
          && !connectorsWithoutCredentials.contains(connectorInstance)) {
        RecordCollection collection = connectorInstance.getRecordCollection();
        for (CredentialGroup credentialGroup : collection.getCredentialGroups()) {
          if (credentialGroup.getConnectorInstances().contains(connectorInstance)) {
            for (UserCredentials userCredentials : userCredentialsList) {
              if (userCredentials.getCredentialGroup().equals(credentialGroup)) {
                connectorCredentials = userCredentials;
                credentialsMap.put(connectorInstance, userCredentials);
                break;
              }
            }
            break;
          }
        }
      }
      if (connectorCredentials == null) {
        connectorsWithoutCredentials.add(connectorInstance);
        LOGGER.warning("Missing credentials for connector " + connectorInstance.getName());
      } else {
        String username = connectorCredentials.getUsername();
        if (StringUtils.isNotBlank(username)) {
          String password = EncryptionUtils.decrypt(connectorCredentials.getEncryptedPassword());
          String domain = connectorCredentials.getDomain();
          Element identityElement = connectorQueryElement.addElement(ServletUtil.XMLTAG_IDENTITY);
          identityElement.setText(username);
          if (StringUtils.isNotBlank(domain)) {
            identityElement.addAttribute(ServletUtil.XMLTAG_DOMAIN_ATTRIBUTE, domain);
          }
          identityElement.addAttribute(ServletUtil.XMLTAG_PASSWORD_ATTRIBUTE, password);

          Element resourceElement = identityElement.addElement(ServletUtil.XMLTAG_RESOURCE);
          resourceElement.setText(record.getUrl());
          resourceElement.addAttribute(
              ServletUtil.XMLTAG_CONNECTOR_NAME_ATTRIBUTE, connectorInstance.getName());
          recordToValidate = true;
        }
      }
    }

    if (recordToValidate) {
      Element response =
          ConnectorManagerRequestUtils.sendPost(connectorManager, "/authorization", document);
      Element authzResponseElement = response.element(ServletUtil.XMLTAG_AUTHZ_RESPONSE);
      List<Element> answerElements = authzResponseElement.elements(ServletUtil.XMLTAG_ANSWER);
      for (Element answerElement : answerElements) {
        Element decisionElement = answerElement.element(ServletUtil.XMLTAG_DECISION);
        boolean permit = decisionElement.getTextTrim().equals("Permit");
        if (permit) {
          Element resourceElement = answerElement.element(ServletUtil.XMLTAG_RESOURCE);
          String recordUrl = resourceElement.getTextTrim();
          Record record = recordsByURLMap.get(recordUrl);
          authorizedRecords.add(record);
        }
      }
    }
    return authorizedRecords;
  }