Skip to content
Snippets Groups Projects
Commit d91aa22e authored by xiaohua guan's avatar xiaohua guan Committed by Yas Naoi
Browse files

Issue #3048125 by Xiaohua Guan, yas: Fix the case if the user change the...

Issue #3048125 by Xiaohua Guan, yas: Fix the case if the user change the .gapps/client_secret.json for Google Spreadsheet of Instance Pricing
parent 322ce68f
No related branches found
No related tags found
No related merge requests found
...@@ -463,7 +463,19 @@ EOF; ...@@ -463,7 +463,19 @@ EOF;
$spreadsheet = \Drupal::service('aws_cloud.google_spreadsheet'); $spreadsheet = \Drupal::service('aws_cloud.google_spreadsheet');
$old_url = $cloud_config->get('field_spreadsheet_pricing_url')->value; $old_url = $cloud_config->get('field_spreadsheet_pricing_url')->value;
if (!empty($old_url)) { if (!empty($old_url)) {
$spreadsheet->delete($old_url); if (aws_cloud_is_google_credential_valid()) {
$spreadsheet->delete($old_url);
}
else {
$page_link = \Drupal::l(t('AWS Cloud Settings'), Url::fromRoute('aws_cloud.settings'));
\Drupal::messenger()->addMessage(
t(
'The content of google credential file is invalid. Please update google credential in @link.',
['@link' => $page_link]
),
'error'
);
}
} }
$url = $spreadsheet->create( $url = $spreadsheet->create(
...@@ -473,6 +485,27 @@ EOF; ...@@ -473,6 +485,27 @@ EOF;
$cloud_config->set('field_spreadsheet_pricing_url', $url); $cloud_config->set('field_spreadsheet_pricing_url', $url);
} }
/**
* Check whether the content of google credential file is valid.
*
* @return bool
* Whether the content of google credential file is valid.
*/
function aws_cloud_is_google_credential_valid() {
$config = \Drupal::config('aws_cloud.settings');
$signature = $config->get('google_credential_signature');
$signature_of_file = '';
$credential_file_path = aws_cloud_google_credential_file_path();
if (file_exists($credential_file_path)) {
$signature_of_file = hash(
'sha256',
json_encode(json_decode(file_get_contents($credential_file_path)))
);
}
return $signature === $signature_of_file;
}
/** /**
* Implements hook_cloud_config_insert(). * Implements hook_cloud_config_insert().
*/ */
...@@ -486,7 +519,13 @@ function aws_cloud_cloud_config_insert(CloudConfig $cloud_config) { ...@@ -486,7 +519,13 @@ function aws_cloud_cloud_config_insert(CloudConfig $cloud_config) {
* Implements hook_cloud_config_update(). * Implements hook_cloud_config_update().
*/ */
function aws_cloud_cloud_config_update(CloudConfig $cloud_config) { function aws_cloud_cloud_config_update(CloudConfig $cloud_config) {
if ($cloud_config->bundle() == 'aws_ec2') { if ($cloud_config->bundle() == 'aws_ec2'
&& !aws_cloud_cloud_configs_equal(
$cloud_config,
$cloud_config->original,
['changed', 'field_spreadsheet_pricing_url']
)
) {
aws_cloud_update_instance_types($cloud_config, TRUE); aws_cloud_update_instance_types($cloud_config, TRUE);
// Update resources. // Update resources.
...@@ -494,6 +533,34 @@ function aws_cloud_cloud_config_update(CloudConfig $cloud_config) { ...@@ -494,6 +533,34 @@ function aws_cloud_cloud_config_update(CloudConfig $cloud_config) {
} }
} }
/**
* Compare two cloud configs.
*
* @param \Drupal\cloud\Entity\CloudConfig $cloud_config1
* One cloud config.
* @param \Drupal\cloud\Entity\CloudConfig $cloud_config2
* Another cloud config.
* @param array $excluded_field_names
* The names of fields excluded.
*
* @return bool
* The result of compariation.
*/
function aws_cloud_cloud_configs_equal(
CloudConfig $cloud_config1,
CloudConfig $cloud_config2,
array $excluded_field_names = []
) {
$field_names = array_keys($cloud_config1->getFields());
$field_names = array_diff($field_names, $excluded_field_names);
foreach ($field_names as $field_name) {
if ($cloud_config1->get($field_name)->value != $cloud_config2->get($field_name)->value) {
return FALSE;
}
}
return TRUE;
}
/** /**
* Update AWS EC2 resources. * Update AWS EC2 resources.
* *
......
...@@ -18,3 +18,4 @@ aws_cloud_volume_notification_minutes: '00' ...@@ -18,3 +18,4 @@ aws_cloud_volume_notification_minutes: '00'
aws_cloud_view_items_per_page: 50 aws_cloud_view_items_per_page: 50
aws_cloud_view_expose_items_per_page: true aws_cloud_view_expose_items_per_page: true
google_credential_file_path: 'private://aws_cloud/.gapps/client_secrets.json' google_credential_file_path: 'private://aws_cloud/.gapps/client_secrets.json'
google_credential_signature: ''
...@@ -49,3 +49,5 @@ aws_cloud.settings: ...@@ -49,3 +49,5 @@ aws_cloud.settings:
type: boolean type: boolean
google_credential_file_path: google_credential_file_path:
type: string type: string
google_credential_signature:
type: string
...@@ -7,6 +7,8 @@ use Drupal\Core\Form\ConfigFormBase; ...@@ -7,6 +7,8 @@ use Drupal\Core\Form\ConfigFormBase;
use Drupal\Core\Form\FormStateInterface; use Drupal\Core\Form\FormStateInterface;
use Drupal\Core\Config\ConfigFactoryInterface; use Drupal\Core\Config\ConfigFactoryInterface;
use Drupal\Core\File\FileSystemInterface; use Drupal\Core\File\FileSystemInterface;
use Drupal\aws_cloud\Service\GoogleSpreadsheetService;
use Drupal\cloud\Plugin\CloudConfigPluginManagerInterface;
use Symfony\Component\DependencyInjection\ContainerInterface; use Symfony\Component\DependencyInjection\ContainerInterface;
...@@ -22,6 +24,20 @@ class AwsCloudAdminSettings extends ConfigFormBase { ...@@ -22,6 +24,20 @@ class AwsCloudAdminSettings extends ConfigFormBase {
*/ */
private $fileSystem; private $fileSystem;
/**
* The google spreadsheet service.
*
* @var \Drupal\aws_cloud\Service\GoogleSpreadsheetService
*/
private $googleSpreadsheetService;
/**
* The cloud config plugin manager.
*
* @var \Drupal\cloud\Plugin\CloudConfigPluginManagerInterface
*/
private $cloudConfigPluginManager;
/** /**
* Constructs a AwsCloudAdminSettings object. * Constructs a AwsCloudAdminSettings object.
* *
...@@ -29,14 +45,22 @@ class AwsCloudAdminSettings extends ConfigFormBase { ...@@ -29,14 +45,22 @@ class AwsCloudAdminSettings extends ConfigFormBase {
* The factory for configuration objects. * The factory for configuration objects.
* @param \Drupal\Core\File\FileSystemInterface $file_system * @param \Drupal\Core\File\FileSystemInterface $file_system
* The file system service. * The file system service.
* @param \Drupal\aws_cloud\Service\GoogleSpreadsheetService $google_spreadsheet_service
* The google spreadsheet service.
* @param \Drupal\cloud\Plugin\CloudConfigPluginManagerInterface $cloud_config_plugin_manager
* The cloud config plugin manager.
*/ */
public function __construct( public function __construct(
ConfigFactoryInterface $config_factory, ConfigFactoryInterface $config_factory,
FileSystemInterface $file_system FileSystemInterface $file_system,
GoogleSpreadsheetService $google_spreadsheet_service,
CloudConfigPluginManagerInterface $cloud_config_plugin_manager
) { ) {
parent::__construct($config_factory); parent::__construct($config_factory);
$this->fileSystem = $file_system; $this->fileSystem = $file_system;
$this->googleSpreadsheetService = $google_spreadsheet_service;
$this->cloudConfigPluginManager = $cloud_config_plugin_manager;
} }
/** /**
...@@ -45,7 +69,9 @@ class AwsCloudAdminSettings extends ConfigFormBase { ...@@ -45,7 +69,9 @@ class AwsCloudAdminSettings extends ConfigFormBase {
public static function create(ContainerInterface $container) { public static function create(ContainerInterface $container) {
return new static( return new static(
$container->get('config.factory'), $container->get('config.factory'),
$container->get('file_system') $container->get('file_system'),
$container->get('aws_cloud.google_spreadsheet'),
$container->get('plugin.manager.cloud_config_plugin')
); );
} }
...@@ -383,7 +409,23 @@ class AwsCloudAdminSettings extends ConfigFormBase { ...@@ -383,7 +409,23 @@ class AwsCloudAdminSettings extends ConfigFormBase {
$time .= ':' . Html::escape($value); $time .= ':' . Html::escape($value);
} }
// If 'google_credential_file_path' is specified, store the
// signature of the JSON file at 'google_credential_file_path'.
// If 'google_credential' w/ the credentail value is specfied,
// use the signature of the 'google_credential'.
if ($key == 'google_credential') { if ($key == 'google_credential') {
if (empty($value)) {
$value = file_get_contents(
$form_state->getValue('google_credential_file_path')
);
}
if (!empty($value)) {
$config->set(
'google_credential_signature',
hash('sha256', json_encode(json_decode($value)))
);
}
continue; continue;
} }
...@@ -514,6 +556,12 @@ class AwsCloudAdminSettings extends ConfigFormBase { ...@@ -514,6 +556,12 @@ class AwsCloudAdminSettings extends ConfigFormBase {
$credential_dir, $credential_dir,
FILE_CREATE_DIRECTORY | FILE_MODIFY_PERMISSIONS FILE_CREATE_DIRECTORY | FILE_MODIFY_PERMISSIONS
)) { )) {
// If credential changed, the old google spreadsheets should be deleted.
$cloud_configs_changed = [];
if ($this->isGoogleCredentialChanged($credential_file_path, $credential)) {
$cloud_configs_changed = $this->deleteGoogleSpreadsheets();
}
file_unmanaged_save_data($credential, $credential_file_path, FILE_EXISTS_REPLACE); file_unmanaged_save_data($credential, $credential_file_path, FILE_EXISTS_REPLACE);
if (empty($old_credential_file_path)) { if (empty($old_credential_file_path)) {
...@@ -526,7 +574,58 @@ class AwsCloudAdminSettings extends ConfigFormBase { ...@@ -526,7 +574,58 @@ class AwsCloudAdminSettings extends ConfigFormBase {
) { ) {
file_unmanaged_delete($old_credential_file_path); file_unmanaged_delete($old_credential_file_path);
} }
// Save cloud configs changed.
// The spreadsheets belonging to them will updated by hook function.
foreach ($cloud_configs_changed as $cloud_config) {
$cloud_config->save();
}
}
}
/**
* Check whether the google credential changed.
*
* @param string $credential_file_path
* The file path of google credential.
* @param string $new_credential
* The new google credential content.
*
* @return bool
* Whether the google credential changed or not.
*/
private function isGoogleCredentialChanged($credential_file_path, $new_credential) {
if (!file_exists($credential_file_path)) {
return TRUE;
}
$old_credential = file_get_contents($credential_file_path);
if ($old_credential === FALSE) {
return TRUE;
}
return trim($old_credential) !== trim($new_credential);
}
/**
* Delete old google spreadsheets.
*
* @return array
* The cloud configs changed.
*/
private function deleteGoogleSpreadsheets() {
$cloud_configs = $this->cloudConfigPluginManager->loadConfigEntities('aws_ec2');
$cloud_configs_changed = [];
foreach ($cloud_configs as $cloud_config) {
$old_url = $cloud_config->get('field_spreadsheet_pricing_url')->value;
if (!empty($old_url)) {
$this->googleSpreadsheetService->delete($old_url);
$cloud_config->set('field_spreadsheet_pricing_url', '');
$cloud_configs_changed[] = $cloud_config;
}
} }
return $cloud_configs_changed;
} }
} }
...@@ -275,10 +275,10 @@ class GoogleSpreadsheetService { ...@@ -275,10 +275,10 @@ class GoogleSpreadsheetService {
); );
} }
} }
catch (\InvalidArgumentException $e) { catch (\Exception $e) {
$this->messenger->addError( $this->messenger->addError(
$this->t( $this->t(
'Failed to create spreadsheet due to the InvalidArgumentException with error "@message"', 'Failed to create spreadsheet due to the Exception with error "@message"',
['@message' => $e->getMessage()] ['@message' => $e->getMessage()]
) )
); );
...@@ -313,10 +313,10 @@ class GoogleSpreadsheetService { ...@@ -313,10 +313,10 @@ class GoogleSpreadsheetService {
); );
} }
} }
catch (\InvalidArgumentException $e) { catch (\Exception $e) {
$this->messenger->addError( $this->messenger->addError(
$this->t( $this->t(
'Failed to delete spreadsheet due to the InvalidArgumentException with error "@message"', 'Failed to delete spreadsheet due to the Exception with error "@message"',
['@message' => $e->getMessage()] ['@message' => $e->getMessage()]
) )
); );
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment