def set_service(request, scheme, hostname, port): encryption = request.GET.get('encryption', 'none') srv_field = request.GET.get('srv', None) kerberos_service = request.GET.get('keytab', None) role = request.GET.get('role', SERVICE) protocol = request.GET.get('protocol', 'tcp') if encryption not in ('none', 'tls', 'starttls'): return HttpResponse('valid encryption levels are none, tls, or starttls') port = int(port) if not (0 <= port <= 65536): return HttpResponse('Invalid port: %s' % port, status=403, content_type='text/plain') if protocol not in ('tcp', 'udp', 'socket'): return HttpResponse('Invalid protocol: %s' % protocol, status=403, content_type='text/plain') description = request.body fqdn = hostname_from_principal(request.user.username) # a few checks if Service.objects.filter(hostname=hostname).exclude(fqdn=fqdn).count() > 0: return HttpResponse(status=401, content='%s is already registered' % hostname) if role not in (SERVICE, KERBEROS_DC, PRINTER, TIME_SERVER, SERVICE_1024): return HttpResponse(status=401, content='Role %s is not allowed' % role) if kerberos_service and kerberos_service not in ('HTTP', 'XMPP', 'smtp', 'IPP', 'ldap', 'cifs', 'imap', 'postgres', 'host'): return HttpResponse(status=401, content='Kerberos service %s is not allowed' % role) hosts = list(Host.objects.filter(fqdn=fqdn)[0:1]) if not hosts: return HttpResponse(status=401, content='Unknown host %s is not allowed' % fqdn) host = hosts[0] if scheme == 'ssh' and host.admin_ip_address != host.main_ip_address: fqdn = '%s.%s%s' % (fqdn.partition('.')[0], settings.PDNS_ADMIN_PREFIX, settings.PENATES_DOMAIN) # Penates service service, created = Service.objects.get_or_create(fqdn=fqdn, scheme=scheme, hostname=hostname, port=port, protocol=protocol) Service.objects.filter(pk=service.pk).update(kerberos_service=kerberos_service, description=description, dns_srv=srv_field, encryption=encryption) # certificates entry = CertificateEntry(hostname, organizationName=settings.PENATES_ORGANIZATION, organizationalUnitName=_('Services'), emailAddress=settings.PENATES_EMAIL_ADDRESS, localityName=settings.PENATES_LOCALITY, countryName=settings.PENATES_COUNTRY, stateOrProvinceName=settings.PENATES_STATE, altNames=[], role=role) pki = PKI() pki.ensure_certificate(entry) if kerberos_service: principal_name = '%s/%s@%s' % (kerberos_service, fqdn, settings.PENATES_REALM) add_principal(principal_name) # DNS part record_name, sep, domain_name = hostname.partition('.') if sep == '.': domains = list(Domain.objects.filter(name=domain_name)[0:1]) if domains: domain = domains[0] domain.ensure_record(fqdn, hostname) domain.set_extra_records(scheme, hostname, port, fqdn, srv_field, entry=entry) domain.update_soa() return HttpResponse(status=201, content='%s://%s:%s/ created' % (scheme, hostname, port))
def get_host_keytab(request, hostname): """Register a computer: - create Kerberos principal - create private key - create public SSH key - create x509 certificate - create PTR DNS record - create A or AAAA DNS record - create SSHFP DNS record - return keytab :param request: :type request: :param hostname: :type hostname: :return: :rtype: """ admin_ip_address = request.GET.get('ip_address') ip_address = request.META.get('HTTP_X_FORWARDED_FOR') short_hostname = hostname.partition('.')[0] domain_name = settings.PENATES_DOMAIN fqdn = '%s.%s%s' % (short_hostname, settings.PDNS_INFRA_PREFIX, domain_name) # valid FQDN # create Kerberos principal principal = principal_from_hostname(fqdn, settings.PENATES_REALM) if principal_exists(principal): return HttpResponse('', status=403) else: add_principal(principal) Host.objects.get_or_create(fqdn=fqdn) # create private key, public key, public certificate, public SSH key entry = entry_from_hostname(fqdn) pki = PKI() pki.ensure_certificate(entry) # create DNS records if ip_address: Domain.ensure_auto_record(ip_address, fqdn, unique=True, override_reverse=True) Host.objects.filter(fqdn=fqdn).update(main_ip_address=ip_address) if admin_ip_address: admin_fqdn = '%s.%s%s' % (short_hostname, settings.PDNS_ADMIN_PREFIX, domain_name) Domain.ensure_auto_record(admin_ip_address, admin_fqdn, unique=True, override_reverse=False) Host.objects.filter(fqdn=fqdn).update(admin_ip_address=admin_ip_address) if settings.OFFER_HOST_KEYTABS: return KeytabResponse(principal) return HttpResponse('', content_type='text/plain', status=201)
def register_host(short_hostname, main_ip_address=None, admin_ip_address=None): fqdn = '%s.%s%s' % (short_hostname, settings.PDNS_INFRA_PREFIX, settings.PENATES_DOMAIN) principal = principal_from_hostname(fqdn, settings.PENATES_REALM) add_principal(principal) Host.objects.get_or_create(fqdn=fqdn) # create private key, public key, public certificate, public SSH key entry = entry_from_hostname(fqdn) pki = PKI() pki.ensure_certificate(entry) # create DNS records if main_ip_address: Domain.ensure_auto_record(main_ip_address, fqdn, unique=True, override_reverse=True) Host.objects.filter(fqdn=fqdn).update(main_ip_address=main_ip_address) if admin_ip_address: admin_fqdn = '%s.%s%s' % (short_hostname, settings.PDNS_ADMIN_PREFIX, settings.PENATES_DOMAIN) Domain.ensure_auto_record(admin_ip_address, admin_fqdn, unique=True, override_reverse=False) Host.objects.filter(fqdn=fqdn).update(admin_ip_address=admin_ip_address) return principal
def save(self, using=None): group = self.set_gid_number() self.cn = self.name self.sn = self.name self.gecos = self.display_name self.ast_account_caller_id = self.display_name self.samba_domain_name = settings.PENATES_REALM self.mail = '%s@%s' % (self.name, settings.PENATES_DOMAIN) self.ast_account_mailbox = self.mail self.home_directory = '/home/%s' % self.name self.set_next_free_value('uid_number') self.samba_sid = '%s-%d' % (get_samba_sid(), self.uid_number) self.primary_group_samba_sid = '%s-%d' % (get_samba_sid(), self.gid_number) super(User, self).save(using=using) if group and self.name not in group.members: group.members.append(self.name) group.save() add_principal(self.principal_name)
def register_host(short_hostname, main_ip_address=None, admin_ip_address=None): fqdn = '%s.%s%s' % (short_hostname, settings.PDNS_INFRA_PREFIX, settings.PENATES_DOMAIN) principal = principal_from_hostname(fqdn, settings.PENATES_REALM) add_principal(principal) Host.objects.get_or_create(fqdn=fqdn) # create private key, public key, public certificate, public SSH key entry = entry_from_hostname(fqdn) pki = PKI() pki.ensure_certificate(entry) # create DNS records if main_ip_address: Domain.ensure_auto_record(main_ip_address, fqdn, unique=True, override_reverse=True) Host.objects.filter(fqdn=fqdn).update(main_ip_address=main_ip_address) if admin_ip_address: admin_fqdn = '%s.%s%s' % (short_hostname, settings.PDNS_ADMIN_PREFIX, settings.PENATES_DOMAIN) Domain.ensure_auto_record(admin_ip_address, admin_fqdn, unique=True, override_reverse=False) Host.objects.filter(fqdn=fqdn).update(admin_ip_address=admin_ip_address) return principal
def save(self, using=None): group = self.set_gid_number() self.cn = self.name self.sn = self.name self.gecos = self.display_name self.ast_account_caller_id = self.display_name self.samba_domain_name = settings.PENATES_REALM self.mail = '%s@%s' % (self.name, settings.PENATES_DOMAIN) self.ast_account_mailbox = self.mail self.home_directory = '/home/%s' % self.name self.set_next_free_value('uid_number') self.samba_sid = '%s-%s' % (get_samba_sid(), self.uid_number) self.primary_group_samba_sid = '%s-%s' % (get_samba_sid(), self.gid_number) super(User, self).save(using=using) if group and self.name not in group.members: # noinspection PyUnresolvedReferences group.members.append(self.name) group.save() add_principal(self.principal_name)
def handle(self, *args, **options): name = '%s@%s' % (options['principal'], settings.PENATES_REALM) add_principal(name) keytab_filename = options['keytab'] if not keytab_filename: return try: exists = os.path.exists(keytab_filename) with open(keytab_filename, 'ab') as fd: fd.write(b'') if not exists: os.remove(keytab_filename) elif keytab_has_principal(name, keytab_filename): return except OSError as e: self.stdout.write(self.style.ERROR('Unable to write file: %s' % keytab_filename)) raise e except ValueError as e: self.stdout.write(self.style.ERROR('Invalid keytab file %s' % keytab_filename)) raise e add_principal_to_keytab(name, keytab_filename)
def handle(self, *args, **options): name = '%s@%s' % (options['principal'], settings.PENATES_REALM) add_principal(name) keytab_filename = options['keytab'] if not keytab_filename: return try: exists = os.path.exists(keytab_filename) with open(keytab_filename, 'ab') as fd: fd.write(b'') if not exists: os.remove(keytab_filename) elif keytab_has_principal(name, keytab_filename): return except OSError as e: self.stdout.write( self.style.ERROR('Unable to write file: %s' % keytab_filename)) raise e except ValueError as e: self.stdout.write( self.style.ERROR('Invalid keytab file %s' % keytab_filename)) raise e add_principal_to_keytab(name, keytab_filename)
def set_service(request, scheme, hostname, port): try: fqdn = hostname_from_principal(request.user.username) except ValueError: return HttpResponse( status=401, content='Unable to create %s://%s:%s/: invalid username' % (scheme, hostname, port)) encryption = request.GET.get('encryption', 'none') srv_field = request.GET.get('srv', None) kerberos_service = request.GET.get('keytab', None) role = request.GET.get('role', SERVICE) protocol = request.GET.get('protocol', 'tcp') if encryption not in ('none', 'tls', 'starttls'): return HttpResponse( 'valid encryption levels are none, tls, or starttls') port = int(port) if not (0 <= port <= 65536): return HttpResponse('Invalid port: %s' % port, status=403, content_type='text/plain') if protocol not in ('tcp', 'udp', 'socket'): return HttpResponse('Invalid protocol: %s' % protocol, status=403, content_type='text/plain') description = request.body # a few checks if Service.objects.filter(hostname=hostname).exclude( fqdn=fqdn).count() > 0: return HttpResponse(status=401, content='%s is already registered' % hostname) if role not in (SERVICE, KERBEROS_DC, PRINTER, TIME_SERVER, SERVICE_1024): return HttpResponse(status=401, content='Role %s is not allowed' % role) if kerberos_service and kerberos_service not in settings.KERBEROS_SERVICES: return HttpResponse(status=401, content='Kerberos service %s is not allowed' % role) hosts = list(Host.objects.filter(fqdn=fqdn)[0:1]) if not hosts: return HttpResponse(status=401, content='Unknown host %s is not allowed' % fqdn) host = hosts[0] if scheme == 'ssh' and host.admin_ip_address != host.main_ip_address: fqdn = '%s.%s%s' % (fqdn.partition('.')[0], settings.PDNS_ADMIN_PREFIX, settings.PENATES_DOMAIN) # Penates service service, created = Service.objects.get_or_create(fqdn=fqdn, scheme=scheme, hostname=hostname, port=port, protocol=protocol, defaults={ 'kerberos_service': kerberos_service, 'dns_srv': srv_field, 'encryption': encryption, 'description': description }) Service.objects.filter(pk=service.pk).update( kerberos_service=kerberos_service, description=description, dns_srv=srv_field, encryption=encryption) # certificates entry = CertificateEntry(hostname, organizationName=settings.PENATES_ORGANIZATION, organizationalUnitName=_('Services'), emailAddress=settings.PENATES_EMAIL_ADDRESS, localityName=settings.PENATES_LOCALITY, countryName=settings.PENATES_COUNTRY, stateOrProvinceName=settings.PENATES_STATE, altNames=[], role=role) pki = PKI() pki.ensure_certificate(entry) if kerberos_service: add_principal(service.principal_name) # DNS part record_name, sep, domain_name = hostname.partition('.') if sep == '.': domains = list(Domain.objects.filter(name=domain_name)[0:1]) if domains: domain = domains[0] domain.ensure_record(fqdn, hostname) domain.set_extra_records(scheme, hostname, port, fqdn, srv_field, entry=entry) domain.update_soa() return HttpResponse(status=201, content='%s://%s:%s/ created' % (scheme, hostname, port))