+ # These attributes should be added to all boxes
+ STANDARD_BOX_ATTRIBUTES = dict({
+ "label" : dict({
+ "name" : "label",
+ "validation_function" : validation.is_string,
+ "type" : Attribute.STRING,
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "help" : "A unique identifier for referring to this box",
+ }),
+ })
+
+ # These are the attribute definitions for tagged attributes
+ STANDARD_TAGGED_ATTRIBUTES_DEFINITIONS = dict({
+ "maxAddresses" : dict({
+ "name" : "maxAddresses",
+ "validation_function" : validation.is_integer,
+ "type" : Attribute.INTEGER,
+ "value" : 1,
+ "flags" : Attribute.DesignReadOnly |\
+ Attribute.ExecInvisible |\
+ Attribute.Metadata,
+ "help" : "The maximum allowed number of addresses",
+ }),
+ })
+
+ # Attributes to be added to all boxes with specific tags
+ STANDARD_TAGGED_BOX_ATTRIBUTES = dict({
+ tags.ALLOW_ADDRESSES : ["maxAddresses"],
+ tags.HAS_ADDRESSES : ["maxAddresses"],
+ })
+
+ # These attributes should be added to all testbeds
+ STANDARD_TESTBED_ATTRIBUTES = dict({
+ "home_directory" : dict({
+ "name" : "homeDirectory",
+ "validation_function" : validation.is_string,
+ "help" : "Path to the directory where traces and other files will be stored",
+ "type" : Attribute.STRING,
+ "value" : "",
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ }),
+ "label" : dict({
+ "name" : "label",
+ "validation_function" : validation.is_string,
+ "type" : Attribute.STRING,
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "help" : "A unique identifier for referring to this testbed",
+ }),
+ })
+
+ # These attributes should be added to all testbeds
+ DEPLOYMENT_ATTRIBUTES = dict({
+ # TESTBED DEPLOYMENT ATTRIBUTES
+ DC.DEPLOYMENT_ENVIRONMENT_SETUP : dict({
+ "name" : DC.DEPLOYMENT_ENVIRONMENT_SETUP,
+ "validation_function" : validation.is_string,
+ "help" : "Shell commands to run before spawning TestbedController processes",
+ "type" : Attribute.STRING,
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.DEPLOYMENT_MODE: dict({
+ "name" : DC.DEPLOYMENT_MODE,
+ "help" : "Instance execution mode",
+ "type" : Attribute.ENUM,
+ "value" : DC.MODE_SINGLE_PROCESS,
+ "allowed" : [
+ DC.MODE_DAEMON,
+ DC.MODE_SINGLE_PROCESS
+ ],
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_enum,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.DEPLOYMENT_COMMUNICATION : dict({
+ "name" : DC.DEPLOYMENT_COMMUNICATION,
+ "help" : "Instance communication mode",
+ "type" : Attribute.ENUM,
+ "value" : DC.ACCESS_LOCAL,
+ "allowed" : [
+ DC.ACCESS_LOCAL,
+ DC.ACCESS_SSH
+ ],
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_enum,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.DEPLOYMENT_HOST : dict({
+ "name" : DC.DEPLOYMENT_HOST,
+ "help" : "Host where the testbed will be executed",
+ "type" : Attribute.STRING,
+ "value" : "localhost",
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_string,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.DEPLOYMENT_USER : dict({
+ "name" : DC.DEPLOYMENT_USER,
+ "help" : "User on the Host to execute the testbed",
+ "type" : Attribute.STRING,
+ "value" : getpass.getuser(),
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_string,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.DEPLOYMENT_KEY : dict({
+ "name" : DC.DEPLOYMENT_KEY,
+ "help" : "Path to SSH key to use for connecting",
+ "type" : Attribute.STRING,
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_string,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.DEPLOYMENT_PORT : dict({
+ "name" : DC.DEPLOYMENT_PORT,
+ "help" : "Port on the Host",
+ "type" : Attribute.INTEGER,
+ "value" : 22,
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_integer,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.ROOT_DIRECTORY : dict({
+ "name" : DC.ROOT_DIRECTORY,
+ "help" : "Root directory for storing process files",
+ "type" : Attribute.STRING,
+ "value" : ".",
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_string, # TODO: validation.is_path
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.USE_AGENT : dict({
+ "name" : DC.USE_AGENT,
+ "help" : "Use -A option for forwarding of the authentication agent, if ssh access is used",
+ "type" : Attribute.BOOL,
+ "value" : False,
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_bool,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.USE_SUDO : dict({
+ "name" : DC.USE_SUDO,
+ "help" : "Use sudo to run the deamon process. This option only take flace when the server runs in daemon mode.",
+ "type" : Attribute.BOOL,
+ "value" : False,
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_bool,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.LOG_LEVEL : dict({
+ "name" : DC.LOG_LEVEL,
+ "help" : "Log level for instance",
+ "type" : Attribute.ENUM,
+ "value" : DC.ERROR_LEVEL,
+ "allowed" : [
+ DC.ERROR_LEVEL,
+ DC.DEBUG_LEVEL
+ ],
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_enum,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ DC.RECOVERY_POLICY : dict({
+ "name" : DC.RECOVERY_POLICY,
+ "help" : "Specifies what action to take in the event of a failure.",
+ "type" : Attribute.ENUM,
+ "value" : DC.POLICY_FAIL,
+ "allowed" : [
+ DC.POLICY_FAIL,
+ DC.POLICY_RECOVER,
+ DC.POLICY_RESTART,
+ ],
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_enum,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ })
+ PROXY_ATTRIBUTES = dict({
+ DC.RECOVER : dict({
+ "name" : DC.RECOVER,
+ "help" : "Do not intantiate testbeds, rather, reconnect to already-running instances. Used to recover from a dead controller.",
+ "type" : Attribute.BOOL,
+ "value" : False,
+ "flags" : Attribute.ExecReadOnly |\
+ Attribute.ExecImmutable |\
+ Attribute.Metadata,
+ "validation_function" : validation.is_bool,
+ "category" : AC.CATEGORY_DEPLOYMENT,
+ }),
+ })
+ PROXY_ATTRIBUTES.update(DEPLOYMENT_ATTRIBUTES)
+
+ # These attributes could appear in the boxes attribute list
+ STANDARD_BOX_ATTRIBUTE_DEFINITIONS = dict({
+ "tun_proto" : dict({
+ "name" : "tun_proto",
+ "help" : "TUNneling protocol used",
+ "type" : Attribute.STRING,
+ "flags" : Attribute.DesignInvisible | \
+ Attribute.ExecInvisible | \
+ Attribute.ExecImmutable | \
+ Attribute.Metadata,
+ "validation_function" : validation.is_string,
+ }),
+ "tun_key" : dict({
+ "name" : "tun_key",
+ "help" : "Randomly selected TUNneling protocol cryptographic key. "
+ "Endpoints must agree to use the minimum (in lexicographic order) "
+ "of both the remote and local sides.",
+ "type" : Attribute.STRING,
+ "flags" : Attribute.DesignInvisible | \
+ Attribute.ExecInvisible | \
+ Attribute.ExecImmutable | \
+ Attribute.Metadata,
+ "validation_function" : validation.is_string,
+ }),
+ "tun_addr" : dict({
+ "name": "tun_addr",
+ "help" : "Address (IP, unix socket, whatever) of the tunnel endpoint",
+ "type" : Attribute.STRING,
+ "flags" : Attribute.DesignInvisible | \
+ Attribute.ExecInvisible | \
+ Attribute.ExecImmutable | \
+ Attribute.Metadata,
+ "validation_function" : validation.is_string,
+ }),
+ "tun_port" : dict({
+ "name" : "tun_port",
+ "help" : "IP port of the tunnel endpoint",
+ "type" : Attribute.INTEGER,
+ "flags" : Attribute.DesignInvisible | \
+ Attribute.ExecInvisible | \
+ Attribute.ExecImmutable | \
+ Attribute.Metadata,
+ "validation_function" : validation.is_integer,
+ }),
+ "tun_cipher" : dict({
+ "name" : "tun_cipher",
+ "help" : "Cryptographic cipher used for tunnelling",
+ "type" : Attribute.ENUM,
+ "value" : "AES",
+ "allowed" : [
+ "AES",
+ "Blowfish",
+ "DES3",
+ "DES",
+ "PLAIN",
+ ],
+ "flags" : Attribute.ExecImmutable,
+ "validation_function" : validation.is_enum,
+ }),
+ ATTR_NEPI_TESTBED_ENVIRONMENT_SETUP : dict({
+ "name" : ATTR_NEPI_TESTBED_ENVIRONMENT_SETUP,
+ "help" : "Commands to set up the environment needed to run NEPI testbeds",
+ "type" : Attribute.STRING,
+ "flags" : Attribute.DesignInvisible | \
+ Attribute.ExecInvisible | \
+ Attribute.ExecImmutable | \
+ Attribute.Metadata,
+ "validation_function" : validation.is_string
+ }),
+ })
+
+ STANDARD_TESTBED_ATTRIBUTES.update(DEPLOYMENT_ATTRIBUTES.copy())
+
+ def __init__(self, testbed_id):