#!/usr/bin/env python
#
# Copyright 2021 VMware, Inc.  All rights reserved. -- VMware Confidential
#
"""
Contains a patch script to disable onprem.mode for gateway.

Patch scripts must be named "patch_XX.py" and must define a unique sub-class
of the PatchBase abstract class. Patches will be sorted by version and will be
applied incrementally.
"""
import logging
import os
import sys
import traceback

if not os.environ['VMWARE_PYTHON_PATH'] in sys.path:
   sys.path.append(os.environ['VMWARE_PYTHON_PATH'])

from .base import PatchBase
from l10n import localizedString, msgMetadata as _T
from distutils.version import LooseVersion
from .file_util import read_properties, write_properties
from .path_constants import H5C_CONFIG_DIR

logger = logging.getLogger(__name__)

DS_PROPS_FILE_PATH = os.path.join(H5C_CONFIG_DIR, "config", "ds.properties")

PROP_NAME_ENABLED_PROTOCOLS = "apigw.security.enabledProtocols"
PROP_NAME_ENABLED_CIPHER_SUITES = "apigw.security.enabledCipherSuites"
PROP_NAME_TRUSTED_ROOTS_CRLS_ENABLED = "apigw.security.TRUSTED_ROOT_CRLS.enabled"

class Patch11(PatchBase):
   """
   Patch to add a few API Gateway properties into file ds.properties, if they are missing
   """

   def __init__(self):
      """
      Constructor
      Set the patch version and summary.
      """

      name = "patch_11"
      version = LooseVersion("11.0")
      summary = localizedString(_T(
            "vsphere.ui.patch11.summary",
            "This patch adds a few API Gateway properties into file ds.properties"))
      PatchBase.__init__(self, name, version, summary)
      self.props = read_properties(DS_PROPS_FILE_PATH)

   def should_patch(self, patch_context):
      """
      :return: Whether the patch should be executed or not
      :rtype: bool
      """
      return not (PROP_NAME_ENABLED_PROTOCOLS in self.props and
                     PROP_NAME_ENABLED_CIPHER_SUITES in self.props and
                     PROP_NAME_TRUSTED_ROOTS_CRLS_ENABLED in self.props)

   def do_patching(self, patch_context):
      logger.info("Patch11: Adding properties to " + DS_PROPS_FILE_PATH)

      if not PROP_NAME_ENABLED_PROTOCOLS in self.props:
         self.props[PROP_NAME_ENABLED_PROTOCOLS] = "TLSv1.2"
         logger.info("Patch11: Added property " + PROP_NAME_ENABLED_PROTOCOLS)

      if not PROP_NAME_ENABLED_CIPHER_SUITES in self.props:
         self.props[PROP_NAME_ENABLED_CIPHER_SUITES] = "TLS_ECDHE_ECDSA_WITH_AES_128_GCM_SHA256,TLS_ECDHE_ECDSA_WITH_AES_256_GCM_SHA384,TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256,TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384"
         logger.info("Patch11: Added property " + PROP_NAME_ENABLED_CIPHER_SUITES)

      if not PROP_NAME_TRUSTED_ROOTS_CRLS_ENABLED in self.props:
         self.props[PROP_NAME_TRUSTED_ROOTS_CRLS_ENABLED] = "n"
         logger.info("Patch11: Added property " + PROP_NAME_TRUSTED_ROOTS_CRLS_ENABLED)

      try:
         write_properties(DS_PROPS_FILE_PATH, self.props)
      except:
         exc_type, exc_value, exc_traceback = sys.exc_info()
         errtb = traceback.format_exception(exc_type, exc_value, exc_traceback)
         logger.error("Error updating ds.properties file:\n " + "".join(errtb))
