#!/usr/bin/python2.6
#
# Copyright 2011-2012 Univention GmbH
#
# http://www.univention.de/
#
# All rights reserved.
#
# The source code of this program is made available
# under the terms of the GNU Affero General Public License version 3
# (GNU AGPL V3) as published by the Free Software Foundation.
#
# Binary versions of this program provided by Univention to you as
# well as other copyrighted, protected or trademarked materials like
# Logos, graphics, fonts, specific documentations and configurations,
# cryptographic keys etc. are subject to a license agreement between
# you and Univention and not subject to the GNU AGPL V3.
#
# In the case you use this program under the terms of the GNU AGPL V3,
# the program is provided in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU Affero General Public License for more details.
#
# You should have received a copy of the GNU Affero General Public
# License with the Debian GNU/Linux or Univention distribution in file
# /usr/share/common-licenses/AGPL-3; if not, see
# <http://www.gnu.org/licenses/>.

'''
This tool prints all DNS forward and reverse zones which are probably invalid (some nameserver or contact not ending with a dot)
'''

import sys
from optparse import OptionParser
import univention.admin
import univention.admin.uldap
import univention.admin.config
import univention.admin.modules
import univention.config_registry

if __name__ == '__main__':
	usage = '''%s [--fix]''' % sys.argv[0]
	description = 'Find (and fix) DNS forward and reverse zones with invalid nameserver and/or contact attributes (not containing a trailing dot)'
	parser = OptionParser(usage=usage, description=description)
	
	parser.add_option("-f", "--fix", action="store_true", dest="fix", default=False, help="Fix all zones automatically")
	parser.add_option("-v", "--verbose", action="store_true", dest="verbose", default=False, help="Print more information (nameservers and contacts) about invalid zones")
	
	(options, args) = parser.parse_args()

	univention.admin.modules.update()                                                                                                                                                                  
	                                                                                                                                                                                                   
	# update choices-lists which are defined in LDAP                                                                                                                                                   
	univention.admin.syntax.update_choices()
	
	configRegistry = univention.config_registry.ConfigRegistry()
	configRegistry.load()
	
	
	lo, position = univention.admin.uldap.getAdminConnection()
	co = univention.admin.config.config()
	# Get forward zones
	forward_module = univention.admin.modules.get('dns/forward_zone')
	forward_zones = univention.admin.modules.lookup(forward_module, co, lo, scope='sub', superordinate=None, base=configRegistry.get('ldap_base'), filter=None)
	# Ger reverse zones
	reverse_module = univention.admin.modules.get('dns/reverse_zone')
	reverse_zones = univention.admin.modules.lookup(reverse_module, co, lo, scope='sub', superordinate=None, base=configRegistry.get('ldap_base'), filter=None)
	
	# Check for nameserver or contac entrys not ending with a dot
	count = 0
	for zone in forward_zones + reverse_zones:
		zone.open()
		if filter( lambda x: not x.endswith('.'), zone.get('nameserver') ) or not zone.get('contact').endswith('.'):
			count += 1
			print 'DN: ' + zone.dn
			if options.verbose:
				for ns in zone.get('nameserver'):
					print '  nameserver: ' + ns
				print '  contact: ' + zone.get('contact')
			if options.fix:
				zone.modify()
	if count:
		print
		if options.fix:
			print 'Fixed %d probably invalid zones' % count
		else:
			print 'Found %d probably invalid zones' % count
