blob: 5427a1b64ec5ea07c312a174f884ec02827dea02 [file] [log] [blame]
#!/usr/bin/env python
# Licensed to the Apache Software Foundation (ASF) under one
# or more contributor license agreements. See the NOTICE file
# distributed with this work for additional information
# regarding copyright ownership. The ASF licenses this file
# to you 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.
try:
import os, sys, re
from optparse import Option, OptionParser
from hawqpylib.hawqlib import HawqXMLParser, parse_hosts_file, remove_property_xml, update_xml_property, local_ssh
from gppylib.commands.unix import getLocalHostname, getUserName
from gppylib.db import dbconn
from pygresql.pg import DatabaseError
from gppylib.gplog import setup_hawq_tool_logging, quiet_stdout_logging, enable_verbose_logging
except ImportError, e:
sys.exit('ERROR: Cannot import modules. Please check that you '
'have sourced greenplum_path.sh. Detail: ' + str(e))
logger, log_filename = setup_hawq_tool_logging('hawq_config',getLocalHostname(),getUserName())
def parseargs():
parser = OptionParser(usage="HAWQ config options.")
parser.add_option('-c', '--change', type='string',
help="Change HAWQ Property.")
parser.add_option('-r', '--remove', type='string',
help="Remove HAWQ Property.")
parser.add_option('-s', '--show', type='string',
help="Change HAWQ Property name.")
parser.add_option('-l', '--list', action='store_true',
help="List all HAWQ Properties.")
parser.add_option('--skipvalidation', action='store_true', default=False)
parser.add_option('--ignore-bad-hosts', action='store_true', default=False,
help='Skips copying configuration files on host on which SSH fails')
parser.add_option('-q', '--quiet', action='store_true', default=False)
parser.add_option("-v", "--value",
dest="property_value",
help="Set HAWQ Property value.")
(options, args) = parser.parse_args()
if options.quiet:
quiet_stdout_logging()
if options.change and options.remove:
logger.error("Multiple actions specified. See the --help info.")
parser.exit()
if options.change and not options.property_value:
logger.error("change requested but value not specified")
parser.exit()
if options.show and options.list:
logger.error("Multiple actions specified. See the --help info.")
parser.exit()
if options.show and (options.change or options.remove):
logger.error("Multiple actions specified. See the --help info.")
parser.exit()
if options.list and (options.change or options.remove):
logger.error("Multiple actions specified. See the --help info.")
parser.exit()
if (options.show or options.list) and options.skipvalidation:
logger.error("--skipvalidation can not be combined with --show/--list.")
parser.exit()
return (options, args)
def check_property(hawq_site, property_name, property_value):
if property_name in hawq_site.hawq_dict:
print "GUC %s already exist in hawq-site.xml" % property_name
print "Update it with value: %s" % property_value
item_exist = True
else:
print "GUC %s does not exist in hawq-site.xml" % property_name
print "Try to add it with value: %s" % property_value
item_exist = False
return item_exist
def check_property_valid(hawq_site, property_name = 'None'):
try:
dburl = dbconn.DbURL(port=hawq_site.hawq_dict['hawq_master_address_port'], dbname='template1')
conn = dbconn.connect(dburl, True)
query = "select name, setting from pg_settings where name='%s';" % property_name
rows = dbconn.execSQL(conn, query)
conn.close()
except DatabaseError, ex:
print "Failed to connect to database, this script can only be run when the database is up"
sys.exit(1)
if rows.rowcount == 0:
print "This GUC name is not valid, use --skipvalidation to do force update"
sys.exit(1)
def list_properties(hawq_site):
property_name = 'None'
property_value = 'None'
try:
dburl = dbconn.DbURL(port=hawq_site.hawq_dict['hawq_master_address_port'], dbname='template1')
conn = dbconn.connect(dburl, True)
query = "select name, setting from pg_settings;"
rows = dbconn.execSQL(conn, query)
conn.close()
except DatabaseError, ex:
print "Failed to connect to database, this script can only be run when the database is up"
sys.exit(1)
for row in rows:
property_name = row[0]
property_value = row[1]
print "GUC\t\t: %s" % property_name
print "Value\t\t: %s\n" % property_value
return property_name, property_value
def show_guc(hawq_site, property_name):
property_value = 'None'
try:
dburl = dbconn.DbURL(port=hawq_site.hawq_dict['hawq_master_address_port'], dbname='template1')
conn = dbconn.connect(dburl, True)
query = "show %s;" % property_name
rows = dbconn.execSQL(conn, query)
if rows:
for row in rows:
property_value = row[0]
else:
print "No such GUC exist"
sys.exit(1)
conn.close()
except DatabaseError, ex:
if re.search("unrecognized configuration parameter", ex.__str__()):
print "Failed to retrieve GUC information, guc %s does not exist" % property_name
elif re.search("could not connect to server", ex.__str__()):
print "Failed to retrieve GUC information, the database is not accesible"
else:
print "Failed to retrieve GUC information: %s" % ex.__str__()
sys.exit(1)
print "GUC\t\t: %s" % property_name
print "Value\t\t: %s" % property_value
return None
def show_property(hawq_site, property_name):
if property_name in hawq_site.hawq_dict:
print "GUC\t\t: %s" % property_name
print "Value\t\t: %s" % hawq_site.hawq_dict[property_name]
else:
print "Failed to retrieve GUC information, guc '%s' does not exist in hawq-site.xml" % property_name
return None
def update_hawq_site(org_config_file, hawq_site, property_name, property_value):
result = check_property(hawq_site, property_name, property_value)
update_xml_property(org_config_file, property_name, property_value)
def sync_hawq_site(config_dir, host_list, ignore_bad_hosts):
sync_host_str = ""
for node in host_list:
sync_host_str += " -h %s" % node
result = local_ssh("hawq scp %s %s %s/etc/hawq-site.xml =:%s/etc/" % (sync_host_str, ignore_bad_hosts, config_dir, config_dir), logger)
if result != 0:
sys.exit("sync hawq-site.xml failed.")
if __name__ == '__main__':
options, args = parseargs()
GPHOME = os.getenv('GPHOME')
if not GPHOME:
sys.exit("GPHOME environment variable not set, exit")
hawq_site = HawqXMLParser(GPHOME)
hawq_site.get_all_values()
org_config_file = "%s/etc/hawq-site.xml" % GPHOME
segment_list = parse_hosts_file(GPHOME)
master_host = hawq_site.hawq_dict['hawq_master_address_host']
host_list = segment_list + [master_host]
ignore_bad_hosts = '--ignore-bad-hosts' if options.ignore_bad_hosts else ''
if 'hawq_standby_address_host' in hawq_site.hawq_dict:
standby_host = hawq_site.hawq_dict['hawq_standby_address_host']
if standby_host not in ('None', 'none', ''):
host_list = host_list + [standby_host]
# Update hawq-site.xml
if options.change:
if not options.property_value:
print "Please specify GUC value"
sys.exit(1)
if not options.skipvalidation:
check_property_valid(hawq_site, options.change)
update_hawq_site(org_config_file, hawq_site, options.change, options.property_value)
sync_hawq_site(GPHOME, host_list, ignore_bad_hosts)
if not options.quiet:
latest_hawq_site = HawqXMLParser(GPHOME)
latest_hawq_site.get_all_values()
show_property(latest_hawq_site, options.change)
elif options.show:
latest_hawq_site = HawqXMLParser(GPHOME)
latest_hawq_site.get_all_values()
show_guc(latest_hawq_site, options.show)
elif options.list:
latest_hawq_site = HawqXMLParser(GPHOME)
latest_hawq_site.get_all_values()
list_properties(latest_hawq_site)
elif options.remove:
except_list = ['hawq_master_address_host', 'hawq_master_directory', 'hawq_segment_directory']
if options.remove in except_list:
print "Remove %s is not allowed" % options.remove
sys.exit(1)
remove_property_xml(options.remove, org_config_file, options.quiet)
sync_hawq_site(GPHOME, host_list, ignore_bad_hosts)
else:
print "Please input correct options"
sys.exit(1)