예제 #1
0
class CreateGA(base.CreateCommand):
    """Create a VPN tunnel.

    *{command}* is used to create a VPN tunnel between a VPN Gateway
  in Google Cloud Platform and an external gateway that is
  identified by --peer-address.
  """

    _TARGET_VPN_GATEWAY_ARG = (
        target_vpn_gateway_flags.TargetVpnGatewayArgumentForVpnTunnel(
            required=True))

    @classmethod
    def _AddCommonFlags(cls, parser):
        _ROUTER_ARG.AddArgument(parser)

        parser.add_argument(
            '--description',
            help='An optional, textual description for the VPN tunnel.')

        parser.add_argument(
            '--ike-version',
            choices=[1, 2],
            type=int,
            help='Internet Key Exchange protocol version number. Default is 2.'
        )

        parser.add_argument('--shared-secret',
                            type=ValidateSimpleSharedSecret,
                            required=True,
                            help="""\
        Shared secret consisting of printable characters.  Valid
        arguments match the regular expression """ + _PRINTABLE_CHARS_PATTERN)

        parser.add_argument('--ike-networks',
                            type=arg_parsers.ArgList(min_length=1),
                            hidden=True,
                            help='THIS ARGUMENT NEEDS HELP TEXT.')

    @classmethod
    def Args(cls, parser):
        """Adds arguments to the supplied parser."""
        parser.display_info.AddFormat(flags.DEFAULT_LIST_FORMAT)

        cls._TARGET_VPN_GATEWAY_ARG.AddArgument(parser)
        _VPN_TUNNEL_ARG.AddArgument(parser, operation_type='create')
        cls._AddCommonFlags(parser)

        parser.add_argument(
            '--peer-address',
            required=True,
            help='Valid IP-v4 address representing the remote tunnel endpoint')

        parser.add_argument('--local-traffic-selector',
                            type=arg_parsers.ArgList(min_length=1),
                            metavar='CIDR',
                            help=("""\
        Traffic selector is an agreement between IKE peers to permit traffic
        through a tunnel if the traffic matches a specified pair of local and
        remote addresses; this flag can only be specified for Classic VPN
        tunnels.

        --local-traffic-selector allows to configure the local addresses that
        are permitted. The value should be a comma separated list of CIDR
        formatted strings. Example: 192.168.0.0/16,10.0.0.0/24.
        """))

        parser.add_argument('--remote-traffic-selector',
                            type=arg_parsers.ArgList(min_length=1),
                            metavar='CIDR',
                            help=("""\
        Traffic selector is an agreement between IKE peers to permit traffic
        through a tunnel if the traffic matches a specified pair of local and
        remote addresses; this flag can only be specified for Classic VPN
        tunnels.

        --remote-traffic-selector allows to configure the remote addresses
        that are permitted. The value should be a comma separated list
        of CIDR formatted strings. Example: 192.168.0.0/16,10.0.0.0/24.
        """))

        parser.display_info.AddCacheUpdater(flags.VpnTunnelsCompleter)

    def _ValidateHighAvailabilityVpnArgs(self, args):
        if args.IsSpecified('vpn_gateway'):
            if not args.IsSpecified('interface'):
                raise exceptions.InvalidArgumentException(
                    '--interface',
                    'When creating High Availability VPN tunnels, the VPN gateway '
                    'interface must be specified using the --interface flag.')
            if not args.IsSpecified('router'):
                raise exceptions.InvalidArgumentException(
                    '--router',
                    'When creating High Availability VPN tunnels, a Cloud Router '
                    'must be specified using the --router flag.')
            if not args.IsSpecified(
                    'peer_gcp_gateway') and not args.IsSpecified(
                        'peer_external_gateway'):
                raise exceptions.InvalidArgumentException(
                    '--peer-gcp-gateway',
                    'When creating High Availability VPN tunnels, either '
                    'peerGcpGateway or peerExternalGateway must be specified.')
            if args.IsSpecified(
                    'peer_external_gateway'
            ) and not args.IsSpecified('peer_external_gateway_interface'):
                raise exceptions.InvalidArgumentException(
                    '--peer-external-gateway-interface',
                    'The flag peer-external-gateway-interface must be spcified along '
                    'with peer-external-gateway.')
            if args.IsSpecified('local_traffic_selector'):
                raise exceptions.InvalidArgumentException(
                    '--local-traffic-selector',
                    'Cannot specify local traffic selector with High Availability '
                    'VPN tunnels.')
            if args.IsSpecified('remote_traffic_selector'):
                raise exceptions.InvalidArgumentException(
                    '--remote-traffic-selector',
                    'Cannot specify remote traffic selector with High Availability '
                    'VPN tunnels.')
            if args.IsSpecified('peer_address'):
                raise exceptions.InvalidArgumentException(
                    '--peer-address',
                    'Cannot specify the flag peer address with High Availability '
                    'VPN tunnels.')

    def _ValidateClassicVpnArgs(self, args):
        if args.IsSpecified('target_vpn_gateway'):
            if not args.IsSpecified('peer_address'):
                raise exceptions.InvalidArgumentException(
                    '--peer-address',
                    'When creating Classic VPN tunnels, the peer address '
                    'must be specified.')

    def _GetPeerGcpGateway(self, api_resource_registry, args):
        if args.IsSpecified('peer_gcp_gateway'):
            peer_gcp_gateway = self._PEER_GCP_GATEWAY_ARG.ResolveAsResource(
                args, api_resource_registry).SelfLink()
            return peer_gcp_gateway
        return None

    def _GetPeerExternalGateway(self, api_resource_registry, args):
        if args.IsSpecified('peer_external_gateway'):
            peer_external_gateway = self._EXTERNAL_VPN_GATEWAY_ARG.ResolveAsResource(
                args, api_resource_registry).SelfLink()
            return peer_external_gateway
        return None

    def _Run(self, args, is_vpn_gateway_supported):
        holder = base_classes.ComputeApiHolder(self.ReleaseTrack())
        client = holder.client
        helper = vpn_tunnels_utils.VpnTunnelHelper(holder)

        # TODO(b/38253176) Add test coverage
        if args.ike_networks is not None:
            raise DeprecatedArgumentException(
                '--ike-networks',
                'It has been renamed to --local-traffic-selector.')

        vpn_tunnel_ref = _VPN_TUNNEL_ARG.ResolveAsResource(
            args,
            holder.resources,
            scope_lister=compute_flags.GetDefaultScopeLister(client))

        router_link = None
        if args.IsSpecified('router'):
            args.router_region = vpn_tunnel_ref.region
            router_ref = _ROUTER_ARG.ResolveAsResource(args, holder.resources)
            router_link = router_ref.SelfLink()

        target_vpn_gateway = None
        vpn_gateway = None
        vpn_gateway_interface = None
        peer_external_gateway = None
        peer_external_gateway_interface = None
        peer_gcp_gateway = None

        if is_vpn_gateway_supported and args.IsSpecified('vpn_gateway'):
            self._ValidateHighAvailabilityVpnArgs(args)
            args.vpn_gateway_region = vpn_tunnel_ref.region
            vpn_gateway = self._VPN_GATEWAY_ARG.ResolveAsResource(
                args, holder.resources).SelfLink()
            vpn_gateway_interface = args.interface
            peer_external_gateway = self._GetPeerExternalGateway(
                holder.resources, args)
            peer_external_gateway_interface = args.peer_external_gateway_interface
            peer_gcp_gateway = self._GetPeerGcpGateway(holder.resources, args)
        else:
            self._ValidateClassicVpnArgs(args)
            args.target_vpn_gateway_region = vpn_tunnel_ref.region
            target_vpn_gateway = self._TARGET_VPN_GATEWAY_ARG.ResolveAsResource(
                args, holder.resources).SelfLink()

        if target_vpn_gateway:
            vpn_tunnel_to_insert = helper.GetClassicVpnTunnelForInsert(
                name=vpn_tunnel_ref.Name(),
                description=args.description,
                ike_version=args.ike_version,
                peer_ip=args.peer_address,
                shared_secret=args.shared_secret,
                target_vpn_gateway=target_vpn_gateway,
                router=router_link,
                local_traffic_selector=args.local_traffic_selector,
                remote_traffic_selector=args.remote_traffic_selector)
        else:
            vpn_tunnel_to_insert = helper.GetHighAvailabilityVpnTunnelForInsert(
                name=vpn_tunnel_ref.Name(),
                description=args.description,
                ike_version=args.ike_version,
                # TODO(b/127839209): remove peer_ip for HA tunnels once peer gateway
                # feature is enabled in Arcus.
                peer_ip=args.peer_address,
                shared_secret=args.shared_secret,
                vpn_gateway=vpn_gateway,
                vpn_gateway_interface=vpn_gateway_interface,
                router=router_link,
                peer_external_gateway=peer_external_gateway,
                peer_external_gateway_interface=peer_external_gateway_interface,
                peer_gcp_gateway=peer_gcp_gateway)

        operation_ref = helper.Create(vpn_tunnel_ref, vpn_tunnel_to_insert)
        return helper.WaitForOperation(vpn_tunnel_ref, operation_ref,
                                       'Creating VPN tunnel')

    def Run(self, args):
        """Issues API requests to construct VPN Tunnels."""
        return self._Run(args, is_vpn_gateway_supported=False)
예제 #2
0
    def Args(cls, parser):
        """Adds arguments to the supplied parser."""

        cls.ROUTER_ARG = router_flags.RouterArgumentForVpnTunnel(
            required=False)
        cls.TARGET_VPN_GATEWAY_ARG = (
            target_vpn_gateway_flags.TargetVpnGatewayArgumentForVpnTunnel())
        cls.TARGET_VPN_GATEWAY_ARG.AddArgument(parser)
        cls.VPN_TUNNEL_ARG = flags.VpnTunnelArgument()
        cls.VPN_TUNNEL_ARG.AddArgument(parser, operation_type='create')

        parser.add_argument(
            '--description',
            help='An optional, textual description for the target VPN tunnel.')

        parser.add_argument(
            '--ike-version',
            choices=[1, 2],
            type=int,
            help='Internet Key Exchange protocol version number. Default is 2.'
        )

        parser.add_argument(
            '--peer-address',
            required=True,
            help='A valid IP-v4 address representing the remote tunnel endpoint'
        )

        # TODO(b/36053573) Add other group members
        parser.add_argument('--shared-secret',
                            type=ValidateSimpleSharedSecret,
                            required=True,
                            help="""\
        A shared secret consisting of printable characters.  Valid
        arguments match the regular expression """ + _PRINTABLE_CHARS_PATTERN)

        parser.add_argument('--ike-networks',
                            type=arg_parsers.ArgList(min_length=1),
                            help=argparse.SUPPRESS)

        parser.add_argument(
            '--local-traffic-selector',
            type=arg_parsers.ArgList(min_length=1),
            metavar='CIDR',
            help=
            ('Traffic selector is an agreement between IKE peers to permit '
             'traffic through a tunnel if the traffic matches a specified pair'
             ' of local and remote addresses.\n\n'
             'local_traffic_selector allows to configure the local addresses '
             'that are permitted. The value should be a comma separated list '
             'of CIDR formatted strings. '
             'Example: 192.168.0.0/16,10.0.0.0/24.'))

        parser.add_argument(
            '--remote-traffic-selector',
            type=arg_parsers.ArgList(min_length=1),
            metavar='CIDR',
            help=
            ('Traffic selector is an agreement between IKE peers to permit '
             'traffic through a tunnel if the traffic matches a specified pair'
             ' of local and remote addresses.\n\n'
             'remote_traffic_selector allows to configure the remote addresses'
             ' that are permitted. The value should be a comma separated list '
             'of CIDR formatted strings. '
             'Example: 192.168.0.0/16,10.0.0.0/24.'))

        # TODO(b/29072646): autocomplete --router argument
        parser.add_argument('--router',
                            help='The Router to use for dynamic routing.')
예제 #3
0
class CreateAlphaBeta(CreateGA):
    """Create a VPN tunnel.

    *{command}* is used to create a VPN tunnel between a VPN Gateway
  in Google Cloud Platform and an external gateway that is
  identified by --peer-address.
  """

    _TARGET_VPN_GATEWAY_ARG = (
        target_vpn_gateway_flags.TargetVpnGatewayArgumentForVpnTunnel(
            required=False))
    _VPN_GATEWAY_ARG = (
        vpn_gateway_flags.GetVpnGatewayArgumentForOtherResource(
            required=False))

    _EXTERNAL_VPN_GATEWAY_ARG = (
        external_vpn_gateway_flags.ExternalVpnGatewayArgumentForVpnTunnel(
            required=False))

    _PEER_GCP_GATEWAY_ARG = (
        vpn_gateway_flags.GetPeerVpnGatewayArgumentForOtherResource(
            required=False))

    @classmethod
    def Args(cls, parser):
        """Adds arguments to the supplied parser."""
        # TODO(b/129011963): add e2e tests for HA VPN tunnels
        parser.display_info.AddFormat(flags.HA_VPN_LIST_FORMAT)

        _VPN_TUNNEL_ARG.AddArgument(parser, operation_type='create')
        vpn_gateway_group_parser = parser.add_mutually_exclusive_group(
            required=True)
        cls._TARGET_VPN_GATEWAY_ARG.AddArgument(vpn_gateway_group_parser)
        cls._VPN_GATEWAY_ARG.AddArgument(vpn_gateway_group_parser)

        peer_vpn_gateway_group_parser = parser.add_mutually_exclusive_group(
            required=True)
        cls._EXTERNAL_VPN_GATEWAY_ARG.AddArgument(
            peer_vpn_gateway_group_parser)
        cls._PEER_GCP_GATEWAY_ARG.AddArgument(peer_vpn_gateway_group_parser)
        peer_vpn_gateway_group_parser.add_argument(
            '--peer-address',
            required=False,
            help='Valid IP-v4 address representing the remote tunnel endpoint, '
            'the peer address must be specified when creating Classic VPN '
            'tunnels from Classic Target VPN Gateway')

        cls._AddCommonFlags(parser)

        parser.add_argument('--local-traffic-selector',
                            type=arg_parsers.ArgList(min_length=1),
                            metavar='CIDR',
                            help=("""\
        Traffic selector is an agreement between IKE peers to permit traffic
        through a tunnel if the traffic matches a specified pair of local and
        remote addresses.

        --local-traffic-selector allows to configure the local addresses that are
        permitted. The value should be a comma separated list of CIDR formatted
        strings. Example: 192.168.0.0/16,10.0.0.0/24.

        Local traffic selector must be specified only for VPN tunnels that
        do not use dynamic routing with a Cloud Router. Omit this flag when
        creating a tunnel using dynamic routing, including a tunnel for a
        highly available VPN gateway."""))

        parser.add_argument('--remote-traffic-selector',
                            type=arg_parsers.ArgList(min_length=1),
                            metavar='CIDR',
                            help=("""\
        Traffic selector is an agreement between IKE peers to permit traffic
        through a tunnel if the traffic matches a specified pair of local and
        remote addresses.

        --remote-traffic-selector allows to configure the remote addresses that
        are permitted. The value should be a comma separated list of CIDR
        formatted strings. Example: 192.168.0.0/16,10.0.0.0/24.

        Remote traffic selector must be specified for VPN tunnels that do
        not use dynamic routing with a Cloud Router. Omit this flag when
        creating a tunnel using dynamic routing, including a tunnel for a
        highly available VPN gateway."""))

        parser.add_argument('--interface',
                            choices=[0, 1],
                            type=int,
                            required=False,
                            help="""\
        Numeric interface ID of the VPN gateway with which this VPN tunnel
        is associated. This flag is required if the tunnel is being attached
        to a High Availability VPN gateway. This option is only available
        for use with High Availability VPN gateway and must be omitted if the
        tunnel is going to be connected to a Classic VPN gateway.""")

        parser.add_argument('--peer-external-gateway-interface',
                            choices=[0, 1, 2, 3],
                            type=int,
                            required=False,
                            help="""\
        Interface ID of the external VPN gateway to which this VPN tunnel
        is connected to.
        This flag is required if the tunnel is being created from
        a High Availability VPN gateway to an External Vpn Gateway.""")

        parser.display_info.AddCacheUpdater(flags.VpnTunnelsCompleter)

    def Run(self, args):
        """Issues API requests to construct VPN Tunnels."""
        return self._Run(args, is_vpn_gateway_supported=True)
예제 #4
0
from googlecloudsdk.api_lib.compute import base_classes
from googlecloudsdk.api_lib.compute.vpn_tunnels import vpn_tunnels_utils
from googlecloudsdk.calliope import arg_parsers
from googlecloudsdk.calliope import base
from googlecloudsdk.calliope import exceptions
from googlecloudsdk.command_lib.compute import flags as compute_flags
from googlecloudsdk.command_lib.compute.routers import flags as router_flags
from googlecloudsdk.command_lib.compute.target_vpn_gateways import (
    flags as target_vpn_gateway_flags)
from googlecloudsdk.command_lib.compute.vpn_tunnels import flags

_PRINTABLE_CHARS_PATTERN = r'[ -~]+'

_ROUTER_ARG = router_flags.RouterArgumentForVpnTunnel(required=False)
_TARGET_VPN_GATEWAY_ARG = (
    target_vpn_gateway_flags.TargetVpnGatewayArgumentForVpnTunnel())
_VPN_TUNNEL_ARG = flags.VpnTunnelArgument()


class DeprecatedArgumentException(exceptions.ToolException):
    def __init__(self, arg, msg):
        super(DeprecatedArgumentException,
              self).__init__('{0} is deprecated. {1}'.format(arg, msg))


def ValidateSimpleSharedSecret(possible_secret):
    """ValidateSimpleSharedSecret checks its argument is a vpn shared secret.

  ValidateSimpleSharedSecret(v) returns v iff v matches [ -~]+.

  Args: