コード例 #1
0
def run_migrations_online():
    """Run migrations in 'online' mode.

    In this scenario we need to create an Engine
    and associate a connection with the context.

    """
    load_config_or_exit()
    engine = get_engine()

    # In case you are trying to perform column change (size for example)
    # alembic will not handle this automatically.
    # Additional parameter has to be passed into context.configure(compare_type=True)
    # Be aware that output of this can be error-pone. Especially for dialect.
    # We want to keep dialect tight with SQLAlchemy all the time.
    # So in case migration contains import to MySQL dialect (MySQL is used as main backend)
    # then this migration has to written manually - But migration content can still help you
    # how to perform this migration
    connection = engine.connect()
    context.configure(connection=connection, target_metadata=target_metadata)

    try:
        with context.begin_transaction():
            context.run_migrations()
    finally:
        connection.close()
コード例 #2
0
ファイル: log_delete.py プロジェクト: ShaolongHu/beaker
def main(argv=None):

    parser = OptionParser('usage: %prog [options]',
            description='Permanently deletes log files from Beaker and/or '
                'archive server',
            version=__version__)
    parser.add_option('-c', '--config', metavar='FILENAME',
            help='Read configuration from FILENAME')
    parser.add_option('-v', '--verbose', action='store_true',
            help='Print the path/URL of deleted files to stdout')
    parser.add_option('--debug', action='store_true',
            help='Print debugging messages to stderr')
    parser.add_option('--dry-run', action='store_true',
            help='Do not delete any files, and issue ROLLBACK instead of '
                'COMMIT after performing database operations')
    parser.add_option('--limit', default=None, type='int',
        help='Set a limit on the number of jobs whose logs will be deleted')
    parser.set_defaults(verbose=False, debug=False, dry_run=False)
    options, args = parser.parse_args(argv)
    load_config_or_exit(options.config)

    # urllib3 installs a NullHandler, we can just remove it and let the messages propagate
    logging.getLogger('requests.packages.urllib3').handlers[:] = []
    log_to_stream(sys.stderr, level=logging.DEBUG if options.debug else logging.WARNING)
    return log_delete(options.verbose, options.dry_run, options.limit)
コード例 #3
0
def main():
    global opts
    parser = get_parser()
    opts, args = parser.parse_args()

    load_config_or_exit(opts.configfile)

    signal.signal(signal.SIGINT, sigterm_handler)
    signal.signal(signal.SIGTERM, sigterm_handler)

    if opts.foreground:
        log_to_stream(sys.stderr, level=logging.DEBUG)
    else:
        log_to_syslog('beakerd')
        pid_file = opts.pid_file
        if pid_file is None:
            pid_file = config.get("PID_FILE", "/var/run/beaker/beakerd.pid")
        d = daemon.DaemonContext(pidfile=pidfile.TimeoutPIDLockFile(pid_file, acquire_timeout=0),
                                 detach_process=True)
        try:
            d.open()
        except pidlockfile.AlreadyLocked:
            log.fatal("could not acquire lock on %s, exiting" % pid_file)
            sys.stderr.write("could not acquire lock on %s" % pid_file)
            sys.exit(1)

    schedule()
コード例 #4
0
def main():
    parser = get_parser()
    opts, args = parser.parse_args()

    if not opts.productfile and not opts.producturl:
        parser.error(
            'Specify product data to load using --product-file or --product-url'
        )

    load_config_or_exit(opts.configfile)
    log_to_stream(sys.stderr)

    if opts.productfile:
        xml_file = open(opts.productfile, 'rb')
        update_products_from_xml(xml_file)
    elif opts.producturl:
        response = requests.get(opts.producturl,
                                stream=True,
                                headers=dict(Accept='application/%s' %
                                             opts.producturl_header))
        response.raise_for_status()
        mimetype, options = cgi.parse_header(response.headers['Content-Type'])
        if mimetype in ['text/xml', 'application/xml']:
            update_products_from_xml(response.raw)
        elif mimetype == 'application/json':
            update_products_from_json(response.raw)
        else:
            raise ValueError('Resource at %s is %s, should be XML or JSON' %
                             (opts.producturl, mimetype))
コード例 #5
0
def main():
    global opts
    parser = get_parser()
    opts, args = parser.parse_args()

    load_config_or_exit(opts.configfile)

    signal.signal(signal.SIGINT, sigterm_handler)
    signal.signal(signal.SIGTERM, sigterm_handler)

    if opts.foreground:
        log_to_stream(sys.stderr, level=logging.DEBUG)
    else:
        log_to_syslog('beakerd')
        pid_file = opts.pid_file
        if pid_file is None:
            pid_file = config.get("PID_FILE", "/var/run/beaker/beakerd.pid")
        d = daemon.DaemonContext(pidfile=pidfile.TimeoutPIDLockFile(pid_file, acquire_timeout=0),
                                 detach_process=True)
        try:
            d.open()
        except pidlockfile.AlreadyLocked:
            log.fatal("could not acquire lock on %s, exiting" % pid_file)
            sys.stderr.write("could not acquire lock on %s" % pid_file)
            sys.exit(1)

    schedule()
コード例 #6
0
def main():
    parser = get_parser()
    opts, args = parser.parse_args()
    load_config_or_exit(opts.configfile)
    if opts.check and opts.background:
        parser.error(
            '--check --background makes no sense, how will you know the result?'
        )
    if not opts.background:
        log_to_stream(sys.stderr,
                      level=logging.DEBUG if opts.debug else logging.WARNING)
        return doit(opts)
    else:
        pidlockfile = PIDLockFile(PIDFILE)
        existing_pid = pidlockfile.read_pid()
        if existing_pid:
            if process_is_alive(existing_pid):
                sys.stderr.write(
                    'Another beaker-init process is running (pid %s)\n' %
                    existing_pid)
                return 1
            else:
                sys.stderr.write('Pid file %s exists but pid %s is dead, '
                                 'removing the pid file\n' %
                                 (PIDFILE, existing_pid))
                pidlockfile.break_lock()
        with daemon.DaemonContext(pidfile=pidlockfile, detach_process=True):
            log_to_syslog('beaker-init')
            return doit(opts)
コード例 #7
0
ファイル: log_delete.py プロジェクト: qhsong/beaker
def main(argv=None):

    parser = OptionParser('usage: %prog [options]',
            description='Permanently deletes log files from Beaker and/or '
                'archive server',
            version=__version__)
    parser.add_option('-c', '--config', metavar='FILENAME',
            help='Read configuration from FILENAME')
    parser.add_option('-v', '--verbose', action='store_true',
            help='Print the path/URL of deleted files to stdout')
    parser.add_option('--debug', action='store_true',
            help='Print debugging messages to stderr')
    parser.add_option('--dry-run', action='store_true',
            help='Do not delete any files, and issue ROLLBACK instead of '
                'COMMIT after performing database operations')
    parser.add_option('--limit', default=None, type='int',
        help='Set a limit on the number of jobs whose logs will be deleted')
    parser.set_defaults(verbose=False, debug=False, dry_run=False)
    options, args = parser.parse_args(argv)
    load_config_or_exit(options.config)

    # urllib3 installs a NullHandler, we can just remove it and let the messages propagate
    logging.getLogger('requests.packages.urllib3').handlers[:] = []
    log_to_stream(sys.stderr, level=logging.DEBUG if options.debug else logging.WARNING)
    return log_delete(options.verbose, options.dry_run, options.limit)
コード例 #8
0
def main():
    parser = get_parser()
    opts, args = parser.parse_args()
    configfile = opts.configfile
    xml_file = opts.productfile
    load_config_or_exit(configfile)
    log_to_stream(sys.stderr)
    update_products(xml_file)
コード例 #9
0
ファイル: product_update.py プロジェクト: omps/beaker
def main():
    parser = get_parser()
    opts,args = parser.parse_args()
    configfile = opts.configfile
    xml_file = opts.productfile
    load_config_or_exit(configfile)
    log_to_stream(sys.stderr)
    update_products(xml_file)
コード例 #10
0
def main():
    parser = OptionParser(description=__description__, version=__version__)
    parser.add_option('-c', '--config-file')
    parser.add_option('--debug',
                      action='store_true',
                      help='Show detailed information about image creation')
    parser.add_option(
        '--no-upload',
        dest='upload',
        action='store_false',
        help='Skip uploading to Glance, leave image temp file on disk')
    parser.add_option('--os-username', help='OpenStack username')
    parser.add_option('--os-password', help='OpenStack password')
    parser.add_option('--os-tenant-name', help='OpenStack tenant name')
    parser.set_defaults(debug=False, upload=True)
    options, args = parser.parse_args()
    load_config_or_exit(options.config_file)
    log_to_stream(sys.stderr,
                  level=logging.DEBUG if options.debug else logging.WARNING)

    if options.upload:
        # Get a Glance client. This seems more difficult than it should be...
        username = options.os_username or os.environ.get('OS_USERNAME')
        if not username:
            parser.error(
                'Specify username with --os-username or env[OS_USERNAME]')
        password = options.os_password or os.environ.get('OS_PASSWORD')
        if not password:
            parser.error(
                'Specify password with --os-password or env[OS_PASSWORD]')
        tenant_name = options.os_tenant_name or os.environ.get(
            'OS_TENANT_NAME')
        if not tenant_name:
            parser.error(
                'Specify tenant with --os-tenant-name or env[OS_TENANT_NAME]')
        auth_url = config.get('openstack.identity_api_url')
        if not auth_url:
            parser.error(
                'OpenStack Identity API URL is not set in the configuration')
        log.debug('Authenticating to Keystone')
        keystone = keystoneclient.v2_0.client.Client(username=username,
                                                     password=password,
                                                     tenant_name=tenant_name,
                                                     auth_url=auth_url)
        log.debug('Looking up Glance URL in service catalog')
        glance_url = keystone.service_catalog.url_for(
            service_type='image', endpoint_type='publicURL')
        log.debug('Using Glance URL %s', glance_url)
        glance = glanceclient.Client('1',
                                     endpoint=glance_url,
                                     token=keystone.auth_token)
        # Generate and upload the image.
        with session.begin():
            upload_image(glance)
    else:
        print generate_image().name
コード例 #11
0
def main():
    parser = get_parser()
    opts,args = parser.parse_args()
    configfile = opts.configfile
    baseurl = opts.baseurl
    # The base URL is always a directory with a trailing slash
    if not baseurl.endswith('/'):
        baseurl += '/'
    load_config_or_exit(configfile)
    log_to_stream(sys.stderr, level=logging.DEBUG if opts.debug else logging.WARNING)
    if opts.basepath:
        basepath = opts.basepath
    else:
        basepath = get("basepath.harness")
    sys.exit(update_repos(baseurl=baseurl, basepath=basepath))
コード例 #12
0
def main():
    parser = get_parser()
    opts,args = parser.parse_args()
    configfile = opts.configfile
    baseurl = opts.baseurl
    # The base URL is always a directory with a trailing slash
    if not baseurl.endswith('/'):
        baseurl += '/'
    load_config_or_exit(configfile)
    log_to_stream(sys.stderr, level=logging.DEBUG if opts.debug else logging.WARNING)
    if opts.basepath:
        basepath = opts.basepath
    else:
        basepath = get("basepath.harness")
    sys.exit(update_repos(baseurl=baseurl, basepath=basepath))
コード例 #13
0
ファイル: ipxe_image.py プロジェクト: beaker-project/beaker
def main():
    parser = OptionParser(description=__description__, version=__version__)
    parser.add_option("-c", "--config-file")
    parser.add_option("--debug", action="store_true", help="Show detailed information about image creation")
    parser.add_option(
        "--no-upload",
        dest="upload",
        action="store_false",
        help="Skip uploading to Glance, leave image temp file on disk",
    )
    parser.add_option("--os-username", help="OpenStack username")
    parser.add_option("--os-password", help="OpenStack password")
    parser.add_option("--os-tenant-name", help="OpenStack tenant name")
    parser.set_defaults(debug=False, upload=True)
    options, args = parser.parse_args()
    load_config_or_exit(options.config_file)
    log_to_stream(sys.stderr, level=logging.DEBUG if options.debug else logging.WARNING)

    if options.upload:
        # Get a Glance client. This seems more difficult than it should be...
        username = options.os_username or os.environ.get("OS_USERNAME")
        if not username:
            parser.error("Specify username with --os-username or env[OS_USERNAME]")
        password = options.os_password or os.environ.get("OS_PASSWORD")
        if not password:
            parser.error("Specify password with --os-password or env[OS_PASSWORD]")
        tenant_name = options.os_tenant_name or os.environ.get("OS_TENANT_NAME")
        if not tenant_name:
            parser.error("Specify tenant with --os-tenant-name or env[OS_TENANT_NAME]")
        auth_url = config.get("openstack.identity_api_url")
        if not auth_url:
            parser.error("OpenStack Identity API URL is not set in the configuration")
        log.debug("Authenticating to Keystone")
        keystone = keystoneclient.v2_0.client.Client(
            username=username, password=password, tenant_name=tenant_name, auth_url=auth_url
        )
        log.debug("Looking up Glance URL in service catalog")
        glance_url = keystone.service_catalog.url_for(service_type="image", endpoint_type="publicURL")
        log.debug("Using Glance URL %s", glance_url)
        glance = glanceclient.Client("1", endpoint=glance_url, token=keystone.auth_token)
        # Generate and upload the image.
        with session.begin():
            upload_image(glance)
    else:
        print generate_image().name
コード例 #14
0
ファイル: init.py プロジェクト: sujithshankar/beaker
def main():
    parser = get_parser()
    opts, args = parser.parse_args()
    load_config_or_exit(opts.configfile)
    log_to_stream(sys.stderr, level=logging.DEBUG if opts.debug else logging.WARNING)

    from turbogears.database import metadata, bind_metadata
    bind_metadata()
    if opts.downgrade:
        downgrade_db(metadata, opts.downgrade)
    else:
        # if database is empty then initialize it
        if not metadata.bind.table_names():
            init_db(metadata, user_name=opts.user_name, password=opts.password,
                    user_display_name=opts.display_name, user_email_address=opts.email_address)
        else:
            # upgrade to the latest DB version
            upgrade_db(metadata)
コード例 #15
0
def run_migrations_offline():
    """Run migrations in 'offline' mode.

    This configures the context with just a URL
    and not an Engine, though an Engine is acceptable
    here as well.  By skipping the Engine creation
    we don't even need a DBAPI to be available.

    Calls to context.execute() here emit the given string to the
    script output.

    """
    load_config_or_exit()
    url = config.get("sqlalchemy.dburi")
    context.configure(url=url)

    with context.begin_transaction():
        context.run_migrations()
コード例 #16
0
ファイル: env.py プロジェクト: beaker-project/beaker
def run_migrations_offline():
    """Run migrations in 'offline' mode.

    This configures the context with just a URL
    and not an Engine, though an Engine is acceptable
    here as well.  By skipping the Engine creation
    we don't even need a DBAPI to be available.

    Calls to context.execute() here emit the given string to the
    script output.

    """
    load_config_or_exit()
    url = config.get("sqlalchemy.dburi")
    context.configure(url=url)

    with context.begin_transaction():
        context.run_migrations()
コード例 #17
0
ファイル: env.py プロジェクト: pombredanne/beaker-1
def run_migrations_online():
    """Run migrations in 'online' mode.

    In this scenario we need to create an Engine
    and associate a connection with the context.

    """
    load_config_or_exit()
    engine = get_engine()

    connection = engine.connect()
    context.configure(connection=connection, target_metadata=target_metadata)

    try:
        with context.begin_transaction():
            context.run_migrations()
    finally:
        connection.close()
コード例 #18
0
ファイル: refresh_ldap.py プロジェクト: beaker-project/beaker
def main():
    parser = optparse.OptionParser('usage: %prog [options]',
            description=__description__,
            version=__version__)
    parser.add_option('-c', '--config', metavar='FILENAME',
            help='Read configuration from FILENAME')
    parser.add_option('--debug', action='store_true',
            help='Print debugging messages to stderr')
    parser.set_defaults(debug=False)
    options, args = parser.parse_args()
    load_config_or_exit(options.config)
    log_to_stream(sys.stderr, level=logging.DEBUG if options.debug else logging.WARNING)

    # beaker-server ships a cron job to run this command, so exit silently 
    # and quickly if LDAP is not actually enabled.
    if not config.get('identity.ldap.enabled', False):
        return 0

    refresh_ldap()
    return 0
コード例 #19
0
ファイル: env.py プロジェクト: beaker-project/beaker
def run_migrations_online():
    """Run migrations in 'online' mode.

    In this scenario we need to create an Engine
    and associate a connection with the context.

    """
    load_config_or_exit()
    engine = get_engine()

    connection = engine.connect()
    context.configure(
                connection=connection,
                target_metadata=target_metadata
                )

    try:
        with context.begin_transaction():
            context.run_migrations()
    finally:
        connection.close()
コード例 #20
0
ファイル: init.py プロジェクト: ShaolongHu/beaker
def main():
    parser = get_parser()
    opts, args = parser.parse_args()
    load_config_or_exit(opts.configfile)
    log_to_stream(sys.stderr,
                  level=logging.DEBUG if opts.debug else logging.WARNING)

    from turbogears.database import metadata, bind_metadata
    bind_metadata()
    if opts.downgrade:
        downgrade_db(metadata, opts.downgrade)
    else:
        # if database is empty then initialize it
        if not metadata.bind.table_names():
            if not opts.user_name:
                parser.error('Pass --user to create an admin user')
            init_db(metadata)
        else:
            # upgrade to the latest DB version
            upgrade_db(metadata)
    populate_db(opts.user_name, opts.password, opts.display_name,
                opts.email_address)
コード例 #21
0
def main(*args):
    parser = get_parser()
    (options, args) = parser.parse_args(*args)
    load_config_or_exit(options.configfile)
    log_to_stream(sys.stderr)
    interface.start(config)
    reservation_expiry = options.reservation_expiry
    reservation_length = options.reservation_length
    waiting_recipe_age = options.waiting_recipe_age
    delayed_job_age = options.delayed_job_age
    testing = options.testing

    if testing:
        print 'Dry run only, nothing will be sent\n'

    for user in User.query:
        beaker_usage = BeakerUsage(user, reservation_expiry,
                                   reservation_length, waiting_recipe_age,
                                   delayed_job_age)
        expiring_reservations = beaker_usage.expiring_reservations()
        open_in_demand_systems = beaker_usage.open_in_demand_systems()
        delayed_jobs = beaker_usage.delayed_jobs()
        if (expiring_reservations or open_in_demand_systems or delayed_jobs):
            data = {
                'user_name': user.user_name,
                'current_date': datetime.utcnow().strftime("%Y-%m-%d"),
                'beaker_fqdn': absolute_url('/'),
                'reservation_expiry': reservation_expiry,
                'reservation_length': reservation_length,
                'waiting_recipe_age': waiting_recipe_age,
                'delayed_job_age': delayed_job_age,
                'expiring_reservations': expiring_reservations,
                'open_reservations': open_in_demand_systems,
                'delayed_jobs': delayed_jobs
            }
            mail.send_usage_reminder(user, data, testing)
    return
コード例 #22
0
ファイル: refresh_ldap.py プロジェクト: pombredanne/beaker-2
def main():
    parser = optparse.OptionParser('usage: %prog [options]',
                                   description=__description__,
                                   version=__version__)
    parser.add_option('-c',
                      '--config',
                      metavar='FILENAME',
                      help='Read configuration from FILENAME')
    parser.add_option('--debug',
                      action='store_true',
                      help='Print debugging messages to stderr')
    parser.set_defaults(debug=False)
    options, args = parser.parse_args()
    load_config_or_exit(options.config)
    log_to_stream(sys.stderr,
                  level=logging.DEBUG if options.debug else logging.WARNING)

    # beaker-server ships a cron job to run this command, so exit silently
    # and quickly if LDAP is not actually enabled.
    if not config.get('identity.ldap.enabled', False):
        return 0

    refresh_ldap()
    return 0
コード例 #23
0
def main():
    parser = get_parser()
    opts, args = parser.parse_args()
    load_config_or_exit(opts.configfile)
    if opts.check and opts.background:
        parser.error('--check --background makes no sense, how will you know the result?')
    if not opts.background:
        log_to_stream(sys.stderr, level=logging.DEBUG if opts.debug else logging.WARNING)
        return doit(opts)
    else:
        pidlockfile = PIDLockFile(PIDFILE)
        existing_pid = pidlockfile.read_pid()
        if existing_pid:
            if process_is_alive(existing_pid):
                sys.stderr.write('Another beaker-init process is running (pid %s)\n'
                        % existing_pid)
                return 1
            else:
                sys.stderr.write('Pid file %s exists but pid %s is dead, '
                        'removing the pid file\n' % (PIDFILE, existing_pid))
                pidlockfile.break_lock()
        with daemon.DaemonContext(pidfile=pidlockfile, detach_process=True):
            log_to_syslog('beaker-init')
            return doit(opts)
コード例 #24
0
ファイル: usage_reminder.py プロジェクト: omps/beaker
def main(*args):
    parser = get_parser()
    (options, args) = parser.parse_args(*args)
    load_config_or_exit(options.configfile)
    log_to_stream(sys.stderr)
    interface.start(config)
    reservation_expiry = options.reservation_expiry
    reservation_length = options.reservation_length
    waiting_recipe_age = options.waiting_recipe_age
    delayed_job_age = options.delayed_job_age
    testing = options.testing

    if testing:
        print 'Dry run only, nothing will be sent\n'

    for user in User.query:
        beaker_usage = BeakerUsage(user, reservation_expiry, reservation_length,
                                   waiting_recipe_age, delayed_job_age)
        expiring_reservations = beaker_usage.expiring_reservations()
        open_in_demand_systems = beaker_usage.open_in_demand_systems()
        delayed_jobs = beaker_usage.delayed_jobs()
        if (expiring_reservations or open_in_demand_systems or delayed_jobs):
            data = {
                'user_name': user.user_name,
                'current_date': datetime.utcnow().strftime("%Y-%m-%d"),
                'beaker_fqdn': absolute_url('/'),
                'reservation_expiry': reservation_expiry,
                'reservation_length': reservation_length,
                'waiting_recipe_age': waiting_recipe_age,
                'delayed_job_age': delayed_job_age,
                'expiring_reservations': expiring_reservations,
                'open_reservations': open_in_demand_systems,
                'delayed_jobs': delayed_jobs
            }
            mail.send_usage_reminder(user, data, testing)
    return
コード例 #25
0
ファイル: create_kickstart.py プロジェクト: omps/beaker
def main(*args):
    parser = optparse.OptionParser('usage: %prog [options]',
        description=__description__,
        version=__version__)
    parser.add_option('-u', '--user', metavar='USERNAME',
        help='The user we are creating a kickstart for', default='admin')
    parser.add_option('-r', '--recipe-id', metavar='ID',
        help='Recreate kickstart based on recipe ID')
    parser.add_option('-d', '--distro-tree-id', metavar='ID',
        help='Recreate kickstart based on distro ID')
    parser.add_option('-t', '--template-dir', metavar='DIR',
        help='Retrieve templates from DIR')
    parser.add_option('-f', '--system', metavar='FQDN',
        help='Generate kickstart for system identified by FQDN')
    parser.add_option('-m', '--ks-meta', metavar='OPTIONS',
        help='Kickstart meta data')
    parser.add_option('-p', '--kernel-options-post', metavar='OPTIONS',
        help='Kernel options post')
    options, args = parser.parse_args(*args)
    ks_meta = options.ks_meta
    koptions_post = options.kernel_options_post
    template_dir = options.template_dir
    if template_dir:
        add_to_template_searchpath(template_dir)

    if not options.recipe_id:
        if not options.distro_tree_id and not options.system:
            parser.error('Must specify either a recipe or a distro tree and system')
        elif not options.distro_tree_id:
            parser.error('Must specify a distro tree id when passing in a system')
        elif not options.system:
            parser.error('Must specify a system when not specifying a recipe')

    load_config_or_exit()
    with session.begin():
        user = User.by_user_name(options.user)
        ks_appends = None
        recipe = None
        distro_tree = None
        system = None
        install_options = None

        if options.distro_tree_id:
            try:
                distro_tree = DistroTree.by_id(options.distro_tree_id)
            except NoResultFound:
                raise RuntimeError("Distro tree id '%s' does not exist" % options.distro_tree_id)
        if options.system:
            fqdn = options.system
            try:
                system = System.by_fqdn(fqdn, user)
            except NoResultFound:
                raise RuntimeError("System '%s' does not exist" % fqdn)

            if distro_tree and not options.recipe_id:
                install_options = system.manual_provision_install_options(distro_tree)\
                    .combined_with(InstallOptions.from_strings(ks_meta, None, koptions_post))

        if options.recipe_id:
            try:
                recipe = Recipe.by_id(options.recipe_id)
            except NoResultFound:
                raise RuntimeError("Recipe id '%s' does not exist" % options.recipe_id)
            if not recipe.resource and not options.system:
                raise RuntimeError('Recipe must have (or had) a resource'
                                   ' assigned to it')
            if not system:
                system = getattr(recipe.resource, 'system', None)
            if not distro_tree:
                distro_tree = recipe.distro_tree

            install_options = InstallOptions.reduce(chain(
                    [global_install_options()],
                    distro_tree.install_options(),
                    system.install_options(distro_tree),
                    [recipe.generated_install_options(),
                     InstallOptions.from_strings(recipe.ks_meta,
                        recipe.kernel_options, recipe.kernel_options_post),
                     InstallOptions.from_strings(ks_meta, None, koptions_post)]))

            ks_appends = [ks_append.ks_append for ks_append \
                          in recipe.ks_appends]
            user = recipe.recipeset.job.owner

        # Render the kickstart
        rendered_kickstart = generate_kickstart(install_options,
                                                distro_tree=distro_tree,
                                                system=system,
                                                user=user,
                                                recipe=recipe,
                                                ks_appends=ks_appends)
        kickstart = rendered_kickstart.kickstart

    print kickstart
コード例 #26
0
ファイル: create_kickstart.py プロジェクト: xhernandez/beaker
def main(*args):
    parser = optparse.OptionParser('usage: %prog [options]',
        description=__description__,
        version=__version__)
    parser.add_option('-u', '--user', metavar='USERNAME',
        help='The user we are creating a kickstart for', default='admin')
    parser.add_option('-r', '--recipe-id', metavar='ID',
        help='Recreate kickstart based on recipe ID')
    parser.add_option('-d', '--distro-tree-id', metavar='ID',
        help='Recreate kickstart based on distro ID')
    parser.add_option('-t', '--template-dir', metavar='DIR',
        help='Retrieve templates from DIR')
    parser.add_option('-f', '--system', metavar='FQDN',
        help='Generate kickstart for system identified by FQDN')
    parser.add_option('-m', '--ks-meta', metavar='OPTIONS', default='',
        help='Kickstart meta data')
    parser.add_option('-p', '--kernel-options-post', metavar='OPTIONS', default='',
        help='Kernel options post')
    options, args = parser.parse_args(*args)
    ks_meta = options.ks_meta.decode(sys.getfilesystemencoding())
    koptions_post = options.kernel_options_post.decode(sys.getfilesystemencoding())
    template_dir = options.template_dir
    if template_dir:
        add_to_template_searchpath(template_dir)

    if not options.recipe_id:
        if not options.distro_tree_id and not options.system:
            parser.error('Must specify either a recipe or a distro tree and system')
        elif not options.distro_tree_id:
            parser.error('Must specify a distro tree id when passing in a system')
        elif not options.system:
            parser.error('Must specify a system when not specifying a recipe')

    load_config_or_exit()
    with session.begin():
        user = User.by_user_name(options.user.decode(sys.getfilesystemencoding()))
        ks_appends = None
        recipe = None
        distro_tree = None
        system = None
        install_options = None

        if options.distro_tree_id:
            try:
                distro_tree = DistroTree.by_id(options.distro_tree_id)
            except NoResultFound:
                raise RuntimeError("Distro tree id '%s' does not exist" % options.distro_tree_id)
        if options.system:
            fqdn = options.system.decode(sys.getfilesystemencoding())
            try:
                system = System.by_fqdn(fqdn, user)
            except DatabaseLookupError:
                raise RuntimeError("System '%s' does not exist" % fqdn)

            if distro_tree and not options.recipe_id:
                install_options = system.manual_provision_install_options(distro_tree)\
                    .combined_with(InstallOptions.from_strings(ks_meta, None, koptions_post))

        if options.recipe_id:
            try:
                recipe = Recipe.by_id(options.recipe_id)
            except NoResultFound:
                raise RuntimeError("Recipe id '%s' does not exist" % options.recipe_id)
            if not recipe.resource and not options.system:
                raise RuntimeError('Recipe must have (or had) a resource'
                                   ' assigned to it')
            if not system:
                system = getattr(recipe.resource, 'system', None)
            if not distro_tree:
                distro_tree = recipe.distro_tree

            sources = []
            # if distro_tree is specified, distro_tree overrides recipe
            osmajor = distro_tree.distro.osversion.osmajor.osmajor if distro_tree else recipe.installation.osmajor
            osminor = distro_tree.distro.osversion.osminor if distro_tree else recipe.installation.osminor
            variant = distro_tree.variant if distro_tree else recipe.installation.variant
            arch = distro_tree.arch if distro_tree else recipe.installation.arch

            sources.append(install_options_for_distro(osmajor, osminor, variant, arch))
            if distro_tree:
                sources.append(distro_tree.install_options())
            sources.extend(system.install_options(arch, osmajor, osminor))
            sources.append(recipe.generated_install_options())
            sources.append(InstallOptions.from_strings(recipe.ks_meta,
                                                       recipe.kernel_options, recipe.kernel_options_post))
            sources.append(InstallOptions.from_strings(ks_meta, None, koptions_post))

            install_options = InstallOptions.reduce(sources)

            ks_appends = [ks_append.ks_append for ks_append \
                          in recipe.ks_appends]
            user = recipe.recipeset.job.owner

        # Render the kickstart
        installation = recipe.installation if recipe and recipe.installation else \
            FakeInstallation(distro_tree.distro.osversion.osmajor.osmajor,
                             distro_tree.distro.osversion.osminor,
                             distro_tree.distro.name,
                             distro_tree.variant,
                             distro_tree.arch,
                             distro_tree.url_in_lab(lab_controller=system.lab_controller))
        rendered_kickstart = generate_kickstart(install_options=install_options,
                                                distro_tree=distro_tree,
                                                installation=installation,
                                                system=system,
                                                user=user,
                                                recipe=recipe,
                                                ks_appends=ks_appends)
        kickstart = rendered_kickstart.kickstart

    print kickstart
コード例 #27
0
def main(*args):
    parser = optparse.OptionParser('usage: %prog [options]',
                                   description=__description__,
                                   version=__version__)
    parser.add_option('-u',
                      '--user',
                      metavar='USERNAME',
                      help='The user we are creating a kickstart for',
                      default='admin')
    parser.add_option('-r',
                      '--recipe-id',
                      metavar='ID',
                      help='Recreate kickstart based on recipe ID')
    parser.add_option('-d',
                      '--distro-tree-id',
                      metavar='ID',
                      help='Recreate kickstart based on distro ID')
    parser.add_option('-t',
                      '--template-dir',
                      metavar='DIR',
                      help='Retrieve templates from DIR')
    parser.add_option('-f',
                      '--system',
                      metavar='FQDN',
                      help='Generate kickstart for system identified by FQDN')
    parser.add_option('-m',
                      '--ks-meta',
                      metavar='OPTIONS',
                      help='Kickstart meta data')
    parser.add_option('-p',
                      '--kernel-options-post',
                      metavar='OPTIONS',
                      help='Kernel options post')
    options, args = parser.parse_args(*args)
    ks_meta = options.ks_meta
    koptions_post = options.kernel_options_post
    template_dir = options.template_dir
    if template_dir:
        add_to_template_searchpath(template_dir)

    if not options.recipe_id:
        if not options.distro_tree_id and not options.system:
            parser.error(
                'Must specify either a recipe or a distro tree and system')
        elif not options.distro_tree_id:
            parser.error(
                'Must specify a distro tree id when passing in a system')
        elif not options.system:
            parser.error('Must specify a system when not specifying a recipe')

    load_config_or_exit()
    with session.begin():
        user = User.by_user_name(options.user)
        ks_appends = None
        recipe = None
        distro_tree = None
        system = None
        install_options = None

        if options.distro_tree_id:
            try:
                distro_tree = DistroTree.by_id(options.distro_tree_id)
            except NoResultFound:
                raise RuntimeError("Distro tree id '%s' does not exist" %
                                   options.distro_tree_id)
        if options.system:
            fqdn = options.system
            try:
                system = System.by_fqdn(fqdn, user)
            except NoResultFound:
                raise RuntimeError("System '%s' does not exist" % fqdn)

            if distro_tree and not options.recipe_id:
                install_options = system.manual_provision_install_options(distro_tree)\
                    .combined_with(InstallOptions.from_strings(ks_meta, None, koptions_post))

        if options.recipe_id:
            try:
                recipe = Recipe.by_id(options.recipe_id)
            except NoResultFound:
                raise RuntimeError("Recipe id '%s' does not exist" %
                                   options.recipe_id)
            if not recipe.resource and not options.system:
                raise RuntimeError('Recipe must have (or had) a resource'
                                   ' assigned to it')
            if not system:
                system = getattr(recipe.resource, 'system', None)
            if not distro_tree:
                distro_tree = recipe.distro_tree

            install_options = InstallOptions.reduce(
                chain([global_install_options()],
                      distro_tree.install_options(),
                      system.install_options(distro_tree), [
                          recipe.generated_install_options(),
                          InstallOptions.from_strings(
                              recipe.ks_meta, recipe.kernel_options,
                              recipe.kernel_options_post),
                          InstallOptions.from_strings(ks_meta, None,
                                                      koptions_post)
                      ]))

            ks_appends = [ks_append.ks_append for ks_append \
                          in recipe.ks_appends]
            user = recipe.recipeset.job.owner

        # Render the kickstart
        rendered_kickstart = generate_kickstart(install_options,
                                                distro_tree=distro_tree,
                                                system=system,
                                                user=user,
                                                recipe=recipe,
                                                ks_appends=ks_appends)
        kickstart = rendered_kickstart.kickstart

    print kickstart
コード例 #28
0
def main():
    parser = OptionParser(description=__description__, version=__version__)
    parser.add_option('-c', '--config-file')
    parser.add_option('--debug', action='store_true',
                      help='Show detailed information about image creation')
    parser.add_option('--no-upload', dest='upload', action='store_false',
                      help='Skip uploading to Glance, leave image temp file on disk')
    parser.add_option('--os-username', help='OpenStack username')
    parser.add_option('--os-password', help='OpenStack password')
    parser.add_option('--os-tenant-name', help=SUPPRESS_HELP)
    parser.add_option('--os-project-name', help='OpenStack project name')
    parser.add_option('--os-project-domain-name', help='OpenStack project domain name')
    parser.add_option('--os-user-domain-name', help='OpenStack user domain name')
    parser.add_option('--image-visibility', help='OpenStack Image visibility',
                      type='choice',
                      choices=['public', 'private', 'shared', 'community'],
                      default='public',
                      )
    parser.set_defaults(debug=False, upload=True)
    options, args = parser.parse_args()
    load_config_or_exit(options.config_file)
    log_to_stream(sys.stderr, level=logging.DEBUG if options.debug else logging.WARNING)

    if options.upload:
        if not has_keystoneclient:
            raise RuntimeError('python-keystoneclient is not installed')
        if not has_glanceclient:
            raise RuntimeError('python-glanceclient is not installed')
        # Get a Glance client. This seems more difficult than it should be...
        username = options.os_username or os.environ.get('OS_USERNAME')
        if not username:
            parser.error('Specify username with --os-username or env[OS_USERNAME]')
        password = options.os_password or os.environ.get('OS_PASSWORD')
        if not password:
            parser.error('Specify password with --os-password or env[OS_PASSWORD]')
        project_name = options.os_project_name or os.environ.get('OS_PROJECT_NAME')
        # for backwards compat
        if not project_name:
            project_name = options.os_tenant_name or os.environ.get('OS_TENANT_NAME')
        if not project_name:
            parser.error('Specify project with --os-project-name or env[OS_PROJECT_NAME]')

        auth_url = config.get('openstack.identity_api_url')
        if not auth_url:
            parser.error('OpenStack Identity API URL is not set in the configuration')

        user_domain_name = options.os_user_domain_name or \
                           os.environ.get('OS_USER_DOMAIN_NAME')
        project_domain_name = options.os_project_domain_name or \
                              os.environ.get('OS_PROJECT_DOMAIN_NAME')

        log.debug('Authenticating to Keystone')
        keystone = keystoneclient.v3.client.Client(
            username=username,
            password=password,
            project_name=project_name,
            user_domain_name=user_domain_name,
            project_domain_name=project_domain_name,
            auth_url=auth_url)

        log.debug('Looking up Glance URL in service catalog')
        glance_url = keystone.service_catalog.url_for(service_type='image',
                                                      endpoint_type='publicURL')
        log.debug('Using Glance URL %s', glance_url)
        glance = glanceclient.v2.client.Client(glance_url, token=keystone.auth_token)
        # Generate and upload the image.
        with session.begin():
            upload_image(glance, visibility=options.image_visibility)
    else:
        print generate_image(delete=False).name