示例#1
0
    def modify_physical_eth_ipv4(self, args, options):
        """
        POST /modify_physical_eth_ipv4

        >>> modify_physical_eth_ipv4({'method': 'dhcp',
                                      'auto':   True},
                                     {'ifname': 'eth0'})
        """
        self.args = args
        self.options = options

        if not xys.validate(self.args, self.MODIFY_PHYSICAL_ETH_IPV4_SCHEMA):
            raise HttpReqError(415, "invalid arguments for command")

        eth = self._get_valid_eth_ipv4()

        # allow dummy interfaces
        if not (eth['physicalif'] or eth['dummyif']):
            raise HttpReqError(415, "invalid interface, it is not a physical interface")

        self.normalize_inet_options()

        if not os.access(self.CONFIG['interfaces_path'], (os.X_OK | os.W_OK)):
            raise HttpReqError(415, "path not found or not writable or not executable: %r" % self.CONFIG['interfaces_path'])
        elif not self.LOCK.acquire_read(self.CONFIG['lock_timeout']):
            raise HttpReqError(503, "unable to take LOCK for reading after %s seconds" % self.CONFIG['lock_timeout'])

        self.args['auto'] = self.args.get('auto', True)
        self.args['family'] = 'inet'

        conf = {'netIfaces':        {},
                'vlans':            {},
                'customipConfs':    {}}

        netifacesbakfile = None

        try:
            if self.CONFIG['netiface_down_cmd']:
                subprocess.call(self.CONFIG['netiface_down_cmd'].strip().split() + [eth['name']])

            for iface in netifaces.interfaces():
                conf['netIfaces'][iface] = 'reserved'

            conf['netIfaces'][eth['name']] = eth['name']
            conf['vlans'][eth['name']] = {0: eth['name']}
            conf['customipConfs'][eth['name']] = self.args

            filecontent, netifacesbakfile = self.get_interface_filecontent(conf)

            try:
                system.file_writelines_flush_sync(self.CONFIG['interfaces_file'], filecontent)

                if self.args.get('up', True) and self.CONFIG['netiface_up_cmd']:
                    subprocess.call(self.CONFIG['netiface_up_cmd'].strip().split() + [eth['name']])
            except Exception, e:
                if netifacesbakfile:
                    copy2(netifacesbakfile, self.CONFIG['interfaces_file'])
                raise e.__class__(str(e))
            return True
示例#2
0
def ResolvConf(args, options):    # pylint: disable-msg=W0613
    """
    POST /resolv_conf

    >>> resolv_conf({'nameservers': '192.168.0.254'})
    >>> resolv_conf({'nameservers': ['192.168.0.254', '10.0.0.254']})
    >>> resolv_conf({'search': ['toto.tld', 'tutu.tld']
                     'nameservers': ['192.168.0.254', '10.0.0.254']})
    """

    if 'nameservers' in args:
        args['nameservers'] = helpers.extract_scalar(args['nameservers'])
        nameservers = helpers.unique_case_tuple(args['nameservers'])

        if len(nameservers) == len(args['nameservers']):
            args['nameservers'] = list(nameservers)
        else:
            raise HttpReqError(415, "duplicated nameservers in %r" % list(args['nameservers']))

    if 'search' in args:
        args['search'] = helpers.extract_scalar(args['search'])
        search = helpers.unique_case_tuple(args['search'])

        if len(search) == len(args['search']):
            args['search'] = list(search)
        else:
            raise HttpReqError(415, "duplicated search in %r" % list(args['search']))

        if len(''.join(args['search'])) > 255:
            raise HttpReqError(415, "maximum length exceeded for option search: %r" % list(args['search']))

    if not xys.validate(args, RESOLVCONF_SCHEMA):
        raise HttpReqError(415, "invalid arguments for command")

    if not os.access(Rcc['resolvconf_path'], (os.X_OK | os.W_OK)):
        raise HttpReqError(415, "path not found or not writable or not executable: %r" % Rcc['resolvconf_path'])

    if not RESOLVCONFLOCK.acquire_read(Rcc['lock_timeout']):
        raise HttpReqError(503, "unable to take RESOLVCONFLOCK for reading after %s seconds" % Rcc['lock_timeout'])

    resolvconfbakfile = None

    try:
        try:
            resolvconfbakfile = _write_config_file('resolvconf',
                                                   _resolv_conf_variables(args))
            return True
        except Exception, e:
            if resolvconfbakfile:
                copy2(resolvconfbakfile, Rcc['resolvconf_file'])
            raise e.__class__(str(e))
    finally:
        RESOLVCONFLOCK.release()
示例#3
0
def swap_ethernet_interfaces(args):
    """
    POST /swap_ethernet_interfaces
    
    args ex:
    {'name1': "eth0",
     'name2': "eth1"}
    """
    if not xys.validate(args, SWAP_ETH_SCHEMA):
        raise HttpReqError(415, "invalid arguments for command")
    if not NETLOCK.acquire_write(NET_LOCK_TIMEOUT):
        raise HttpReqError(503, "unable to take NETLOCK for writing after %s seconds" % NET_LOCK_TIMEOUT)
    try:
        xivo_config.swap_ethernet_interfaces(args['name1'], args['name2'])
        return True
    finally:
        NETLOCK.release()
示例#4
0
def rename_ethernet_interface(args):
    """
    POST /rename_ethernet_interface
    
    args ex:
    {'old_name': "eth42",
     'new_name': "eth1"}
    """
    if not xys.validate(args, REN_ETH_SCHEMA):
        raise HttpReqError(415, "invalid arguments for command")
    if not NETLOCK.acquire_write(NET_LOCK_TIMEOUT):
        raise HttpReqError(503, "unable to take NETLOCK for writing after %s seconds" % NET_LOCK_TIMEOUT)
    try:
        xivo_config.rename_ethernet_interface(args['old_name'], args['new_name'])
        return True
    finally:
        NETLOCK.release()
示例#5
0
def Hosts(args, options):    # pylint: disable-msg=W0613
    """
    POST /hosts

    >>> hosts({'hostname':  'xivo',
               'domain':    'localdomain'})
    """

    if not xys.validate(args, HOSTS_SCHEMA):
        raise HttpReqError(415, "invalid arguments for command")

    if not os.access(Rcc['hostname_path'], (os.X_OK | os.W_OK)):
        raise HttpReqError(415, "path not found or not writable or not executable: %r" % Rcc['hostname_path'])

    if not os.access(Rcc['hosts_path'], (os.X_OK | os.W_OK)):
        raise HttpReqError(415, "path not found or not writable or not executable: %r" % Rcc['hosts_path'])

    if not RESOLVCONFLOCK.acquire_read(Rcc['lock_timeout']):
        raise HttpReqError(503, "unable to take RESOLVCONFLOCK for reading after %s seconds" % Rcc['lock_timeout'])

    hostnamebakfile = None
    hostsbakfile    = None

    try:
        try:
            hostnamebakfile = _write_config_file('hostname',
                                                 {'_XIVO_HOSTNAME': args['hostname']})

            hostsbakfile    = _write_config_file('hosts',
                                                 {'_XIVO_HOSTNAME': args['hostname'],
                                                  '_XIVO_DOMAIN':   args['domain']})

            if Rcc['hostname_update_cmd']:
                subprocess.call(Rcc['hostname_update_cmd'].strip().split())

            return True
        except Exception, e:
            if hostnamebakfile:
                copy2(hostnamebakfile, Rcc['hostname_file'])
            if hostsbakfile:
                copy2(hostsbakfile, Rcc['hosts_file'])
            raise e.__class__(str(e))
    finally:
        RESOLVCONFLOCK.release()
示例#6
0
    def change_state_eth_ipv4(self, args, options):
        """
        POST /change_state_eth_ipv4

        >>> change_state_eth_ipv4({'state': True},
                                  {'ifname':    'eth0'})
        """
        self.args = args
        self.options = options

        eth = self._get_valid_eth_ipv4()

        if not xys.validate(self.args, self.CHANGE_STATE_ETH_SCHEMA):
            raise HttpReqError(415, "invalid arguments for command")
        elif not self.LOCK.acquire_read(self.CONFIG['lock_timeout']):
            raise HttpReqError(503, "unable to take LOCK for reading after %s seconds" % self.CONFIG['lock_timeout'])

        conf = {'netIfaces':        {},
                'vlans':            {},
                'customipConfs':    {}}

        ret = False
        netifacesbakfile = None

        try:
            for iface in netifaces.interfaces():
                conf['netIfaces'][iface] = 'reserved'

            if self.args['state']:
                eth['auto'] = True
                eth['flags'] |= dumbnet.INTF_FLAG_UP

                if self.CONFIG['netiface_up_cmd'] \
                   and subprocess.call(self.CONFIG['netiface_up_cmd'].strip().split() + [eth['name']]) == 0:
                    ret = True
            else:
                eth['auto'] = False
                eth['flags'] &= ~dumbnet.INTF_FLAG_UP

                if self.CONFIG['netiface_down_cmd'] \
                   and subprocess.call(self.CONFIG['netiface_down_cmd'].strip().split() + [eth['name']]) == 0:
                    ret = True

            eth['ifname'] = eth['name']
            conf['netIfaces'][eth['name']] = eth['name']
            conf['vlans'][eth['name']] = {eth.get('vlan-id', 0): eth['name']}
            conf['customipConfs'][eth['name']] = eth

            filecontent, netifacesbakfile = self.get_interface_filecontent(conf)

            try:
                system.file_writelines_flush_sync(self.CONFIG['interfaces_file'], filecontent)

                if not ret:
                    if not self.args['state'] and eth.has_key('gateway'):
                        del eth['gateway']
                    self.netcfg.set(eth)
            except Exception, e:
                if netifacesbakfile:
                    copy2(netifacesbakfile, self.CONFIG['interfaces_file'])
                raise e.__class__(str(e))
            return True
示例#7
0
    def modify_eth_ipv4(self, args, options):
        """
        POST /modify_eth_ipv4

        >>> modify_eth_ipv4({'address':     '192.168.0.1',
                             'netmask':     '255.255.255.0',
                             'broadcast':   '192.168.0.255',
                             'gateway':     '192.168.0.254',
                             'mtu':         1500,
                             'auto':        True,
                             'up':          True,
                             'options':     [['dns-search', 'toto.tld tutu.tld'],
                                             ['dns-nameservers', '127.0.0.1 192.168.0.254']]},
                            {'ifname':  'eth0'})
        """
        self.args = args
        self.options = options

        eth = self._get_valid_eth_ipv4()

        if not xys.validate(self.args, self.MODIFY_ETH_IPV4_SCHEMA):
            raise HttpReqError(415, "invalid arguments for command")

        if self.args.has_key('up'):
            if self.args['up']:
                eth['flags'] |= dumbnet.INTF_FLAG_UP
            else:
                eth['flags'] &= ~dumbnet.INTF_FLAG_UP
            del self.args['up']

        if not self.args.has_key('broadcast') and eth.has_key('broadcast'):
            del eth['broadcast']

        if not self.args.has_key('gateway') and eth.has_key('gateway'):
            del eth['gateway']

        if not self.args.has_key('mtu') and eth.has_key('mtu'):
            del eth['mtu']

        eth.update(self.args)

        eth['auto'] = self.args.get('auto', True)

        if not xivo_config.plausible_static(eth, None):
            raise HttpReqError(415, "invalid arguments for command")
        elif not os.access(self.CONFIG['interfaces_path'], (os.X_OK | os.W_OK)):
            raise HttpReqError(415, "path not found or not writable or not executable: %r" % self.CONFIG['interfaces_path'])
        elif not self.LOCK.acquire_read(self.CONFIG['lock_timeout']):
            raise HttpReqError(503, "unable to take LOCK for reading after %s seconds" % self.CONFIG['lock_timeout'])

        conf = {'netIfaces':    {},
                'vlans':        {},
                'ipConfs':      {}}

        ret = False
        netifacesbakfile = None

        try:
            if self.CONFIG['netiface_down_cmd'] \
               and subprocess.call(self.CONFIG['netiface_down_cmd'].strip().split() + [eth['name']]) == 0 \
               and not (eth['flags'] & dumbnet.INTF_FLAG_UP):
                ret = True

            for iface in netifaces.interfaces():
                conf['netIfaces'][iface] = 'reserved'

            eth['ifname'] = eth['name']
            conf['netIfaces'][eth['name']] = eth['name']
            conf['vlans'][eth['name']] = {eth.get('vlan-id', 0): eth['name']}
            conf['ipConfs'][eth['name']] = eth

            filecontent, netifacesbakfile = self.get_interface_filecontent(conf)

            try:
                system.file_writelines_flush_sync(self.CONFIG['interfaces_file'], filecontent)

                if self.CONFIG['netiface_up_cmd'] \
                   and (eth['flags'] & dumbnet.INTF_FLAG_UP) \
                   and subprocess.call(self.CONFIG['netiface_up_cmd'].strip().split() + [eth['name']]) == 0:
                    ret = True

                if not ret:
                    if eth.has_key('gateway') and not (eth['flags'] & dumbnet.INTF_FLAG_UP):
                        del eth['gateway']
                    self.netcfg.set(eth)
            except Exception, e:
                if netifacesbakfile:
                    copy2(netifacesbakfile, self.CONFIG['interfaces_file'])
                raise e.__class__(str(e))
            return True
示例#8
0
    def replace_virtual_eth_ipv4(self, args, options):
        """
        POST /replace_virtual_eth_ipv4

        >>> replace_virtual_eth_ipv4({'ifname': 'eth0:0',
                                      'method': 'dhcp',
                                      'auto':   True},
                                     {'ifname': 'eth0:0'})
        """
        self.args = args
        self.options = options
        phyifname = None
        phyinfo = None

        if 'ifname' not in self.options \
           or not isinstance(self.options['ifname'], basestring) \
           or not xivo_config.netif_managed(self.options['ifname']):
            raise HttpReqError(415, "invalid interface name, ifname: %r" % self.options['ifname'])
        elif not xys.validate(self.args, self.REPLACE_VIRTUAL_ETH_IPV4_SCHEMA):
            raise HttpReqError(415, "invalid arguments for command")

        info = self.get_netiface_info(self.options['ifname'])

        if info and info['physicalif']:
            raise HttpReqError(415, "invalid interface, it is a physical interface")
        elif network.is_alias_if(self.args['ifname']):
            phyifname = network.phy_name_from_alias_if(self.args['ifname'])
            phyinfo = self.get_netiface_info(phyifname)
            if not phyinfo or True not in (phyinfo['physicalif'], phyinfo['vlanif']):
                raise HttpReqError(415, "invalid interface, it is not an alias interface")
            elif self.args['method'] != 'static':
                raise HttpReqError(415, "invalid method, must be static")

            if 'vlanrawdevice' in self.args:
                del self.args['vlanrawdevice']
            if 'vlanid' in self.args:
                del self.args['vlanid']
        elif network.is_vlan_if(self.args['ifname']):
            if not 'vlanrawdevice' in self.args:
                raise HttpReqError(415, "invalid arguments for command, missing vlanrawdevice")
            if not 'vlanid' in self.args:
                raise HttpReqError(415, "invalid arguments for command, missing vlanid")

            phyifname = self.args['vlanrawdevice']
            phyinfo = self.get_netiface_info(phyifname)
            if not phyinfo or not phyinfo['physicalif']:
                raise HttpReqError(415, "invalid vlanrawdevice, it is not a physical interface")

            vconfig = network.get_vlan_info_from_ifname(self.args['ifname'])

            if 'vlan-id' not in vconfig:
                raise HttpReqError(415, "invalid vlan interface name")
            elif vconfig['vlan-id'] != int(self.args['vlanid']):
                raise HttpReqError(415, "invalid vlanid")
            elif vconfig.get('vlan-raw-device', self.args['vlanrawdevice']) != self.args['vlanrawdevice']:
                raise HttpReqError(415, "invalid vlanrawdevice")

            self.args['vlan-id'] = self.args.pop('vlanid')
            self.args['vlan-raw-device'] = self.args.pop('vlanrawdevice')
        else:
            raise HttpReqError(415, "invalid ifname argument for command")

        if phyinfo.get('type') != 'eth':
            raise HttpReqError(415, "invalid interface type")
        elif phyinfo.get('family') != 'inet':
            raise HttpReqError(415, "invalid address family")

        self.normalize_inet_options()

        if not os.access(self.CONFIG['interfaces_path'], (os.X_OK | os.W_OK)):
            raise HttpReqError(415, "path not found or not writable or not executable: %r" % self.CONFIG['interfaces_path'])
        elif not self.LOCK.acquire_read(self.CONFIG['lock_timeout']):
            raise HttpReqError(503, "unable to take LOCK for reading after %s seconds" % self.CONFIG['lock_timeout'])

        self.args['auto'] = self.args.get('auto', True)
        self.args['family'] = 'inet'

        conf = {'netIfaces':        {},
                'vlans':            {},
                'customipConfs':    {}}

        netifacesbakfile = None

        try:
            if self.CONFIG['netiface_down_cmd']:
                subprocess.call(self.CONFIG['netiface_down_cmd'].strip().split() + [self.options['ifname']])

            for iface in netifaces.interfaces():
                if self.options['ifname'] != iface:
                    conf['netIfaces'][iface] = 'reserved'

            conf['netIfaces'][self.args['ifname']] = self.args['ifname']
            conf['vlans'][self.args['ifname']] = {self.args.get('vlan-id', 0): self.args['ifname']}
            conf['customipConfs'][self.args['ifname']] = self.args

            filecontent, netifacesbakfile = self.get_interface_filecontent(conf)

            try:
                system.file_writelines_flush_sync(self.CONFIG['interfaces_file'], filecontent)

                if self.args.get('up', True) and self.CONFIG['netiface_up_cmd']:
                    subprocess.call(self.CONFIG['netiface_up_cmd'].strip().split() + [self.args['ifname']])
            except Exception, e:
                if netifacesbakfile:
                    copy2(netifacesbakfile, self.CONFIG['interfaces_file'])
                raise e.__class__(str(e))
            return True