示例#1
0
    def infos(self, exists=True):
        """
        get VenvInfo instances generator.

        Usage
        -----

        ::

            for venv_info in venvs.infos():
                pass

        :param exists: the virtualenv must exist to be included in the generator
        :type exists: bool
        """
        if not self.in_virtualenv and not self.defined:
            raise NoAvailableVirtualenv()
        value = self._ver_attr
        if not is_sequence(value):
            value = [value]
        try:
            for ver in value:
                venv_info = VenvInfo(ver)
                if exists:
                    if venv_info.exists():
                        yield venv_info
                else:
                    yield venv_info
        except Exception as ex:
            error(str(ex))
示例#2
0
            def _app_output(options):
                # noinspection PyArgumentEqualDefault
                with LocalShell(verbose=False) as local:
                    if Project.main is not None:
                        # noinspection PyBroadException
                        executable = ""
                        try:
                            executable = os.path.join(Project.herringfile_dir, Project.package, Project.main)
                            text = local.system(
                                "{exe} {options}".format(exe=executable, options=options), verbose=False
                            )
                            if text:
                                return text
                        except Exception as ex:
                            error('Error running "{exe}" - {why}'.format(exe=executable, why=str(ex)))

                    console_scripts = _console_scripts()
                    output = []
                    for script in console_scripts:
                        try:
                            text = local.system(
                                "python -m {exe} {options}".format(exe=script, options=options), verbose=False
                            )
                            # info("text:  {text}".format(text=text))
                            if text:
                                output.append(text)
                        except Exception as ex:
                            error('Error running "{exe}" - {ex}'.format(exe=script, ex=str(ex)))
                    return "\n".join(output)
示例#3
0
文件: doc.py 项目: royw/herringlib
        def readme():
            """Update the README.rst from the application's package docstring"""
            if Project.generate_readme:
                # noinspection PyBroadException
                try:
                    # make sure the project's directory is on the system path so python can find import modules
                    this_dir = os.path.abspath(Project.herringfile_dir)
                    parent_dir = os.path.dirname(this_dir)
                    if this_dir in sys.path:
                        sys.path.remove(this_dir)
                    if parent_dir in sys.path:
                        sys.path.remove(parent_dir)
                    sys.path.insert(0, parent_dir)
                    sys.path.insert(1, this_dir)

                    debug("sys.path: %s" % pformat(sys.path))
                    debug("package: {pkg}".format(pkg=Project.package))
                    app_module = importlib.import_module(Project.package)
                    text = app_module.__doc__
                    debug(text)
                    if text:
                        with open(Project.readme_file, 'w') as readme_file:
                            readme_file.write(text)
                except Exception as ex:
                    error('Can not write {file} - {why}'.format(file=Project.readme_file, why=str(ex)))
示例#4
0
    def run_process(self, cmd_args, env=None, out_stream=sys.stdout, verbose=True,
                    timeout=0, timeout_interval=.001):
        """
        Run the process yield for each output line from the process.

        :param out_stream:
        :param cmd_args: command line components
        :type cmd_args: list
        :param env: environment
        :type env: dict
        :param verbose: outputs the method call if True
        :type verbose: bool
        :param timeout:
        :type timeout: int
        :param timeout_interval:
        :type timeout_interval: int
        :yields: each line of output as it is generated
        :ytype: str
        """
        self.display("run_process(%s, %s)\n\n" % (cmd_args, env), out_stream=out_stream, verbose=verbose)
        sub_env = os.environ.copy()
        if env:
            for key, value in env.items():
                sub_env[key] = value

        with GracefulInterruptHandler() as handler:
            try:
                # info("PATH={path}".format(path=pformat(sub_env['PATH'].split(':'))))
                # info("sys.path={path}".format(path=pformat(sys.path)))
                process = subprocess.Popen(cmd_args,
                                           stdout=subprocess.PIPE, stderr=subprocess.STDOUT,
                                           env=sub_env)
                fido = Watchdog(timeout)
                try:
                    while process.poll() is None:   # returns None while subprocess is running
                        if handler.interrupted:
                            process.kill()
                        while True:
                            line = self._non_block_read(process.stdout)
                            if not line:
                                break
                            yield line
                        sleep(timeout_interval)
                except Watchdog:
                    process.kill()
                fido.stop()

                line = self._non_block_read(process.stdout)
                if line:
                    yield line
            except OSError as ex:
                error("Error: Unable to run process: {cmd_args} - {err}".format(cmd_args=repr(cmd_args), err=str(ex)))
示例#5
0
def _replace_version_txt_file(version_str, project_package=None):
    file_name = _file_spec('VERSION.txt', project_package)
    try:
        with open(file_name, 'w') as version_file:
            version_file.write(version_str)
    except IOError as ex2:
        error(ex2)
        file_name = _file_spec('VERSION.txt', Project.herringfile_dir)
        try:
            with open(file_name, 'w') as version_file:
                version_file.write(version_str)
        except IOError as ex2:
            error(ex2)
示例#6
0
    def release():
        """Releases the project to github and pypi"""
        if not os.path.exists(os.path.expanduser('~/.pypirc')):
            error('You must have a configured ~/.pypirc file.  '
                  'See http://peterdowns.com/posts/first-time-with-pypi.html'
                  'Hint, do not use comments in your .pypirc')
            return

        github()
        pypi_test()
        if query_yes_no('Is the new package on pypi-test (http://testpypi.python.org/pypi)?'):
            pypi_live()
            upload_docs()
示例#7
0
def set_project_version(version_str, project_package=None):
    """
    Set the version in __init__.py

    :param version_str: the new version string
    :type version_str: str
    :param project_package: the root package
    :type project_package: str
    """

    try:
        _edit_package_version(version_str=version_str, project_package=project_package)
        file_name = _file_spec('VERSION.txt', project_package)
        if os.path.exists(file_name):
            os.remove(file_name)
    except (AttributeError, IOError) as ex:
        error(ex)
        _replace_version_txt_file(version_str=version_str, project_package=project_package)
示例#8
0
        def clean_directory(directory):
            """
            remove all files and directories from the target html directory

            :param directory: the directory to clean
            :type directory: str
            """
            info("clean_directory Project.docs_html_path = {dir}".format(dir=directory))
            if os.path.isdir(directory):
                for the_file in os.listdir(directory):
                    if the_file.startswith("."):
                        continue
                    file_path = os.path.join(directory, the_file)
                    try:
                        if os.path.isfile(file_path):
                            info("unlink {file}".format(file=file_path))
                            os.unlink(file_path)
                        elif os.path.isdir(file_path):
                            info("rmtree {file}".format(file=file_path))
                            shutil.rmtree(file_path)
                    except Exception as e:
                        error(str(e))
示例#9
0
 def __check_missing_required_attributes(self):
     missing_keys = self.__missing_required_attributes()
     for missing_key in missing_keys:
         error("Missing required '{key}' in Project.metadata call in the herringfile.".format(key=missing_key))
     if missing_keys:
         raise Exception('The herringfiles has missing required keys.  Please correct and try again.')
示例#10
0
    def _create_from_template(self, src_filename, dest_filename, **kwargs):
        """
        Render the destination file from the source template file

        Scans the templates directory and create any corresponding files relative
        to the root directory.  If the file is a .template, then renders the file,
        else simply copy it.

        Template files are just string templates which will be formatted with the
        following named arguments:  name, package, author, author_email, and description.

        Note, be sure to escape curly brackets ('{', '}') with double curly brackets ('{{', '}}').

        :param src_filename: the template file
        :param dest_filename: the rendered file
        """
        info("creating {dest} from {src}".format(dest=dest_filename, src=src_filename))
        with open(src_filename) as in_file:
            template = in_file.read()

        new_filename = None
        try:
            # we just want the unique temp file name, we will delete it in the finally block
            tf = tempfile.NamedTemporaryFile(delete=False)
            new_filename = tf.name
            tf.close()

            rendered = template.format(**kwargs)
            with open(new_filename, 'w') as out_file:
                try:
                    out_file.write(rendered)
                # catching all exceptions
                # pylint: disable=W0703
                except Exception as ex:
                    error(ex)

            # if there is a dest_filename, then handle backing it up
            if os.path.isfile(dest_filename):
                # new_filename contains the just rendered template
                # dest_filename contains the original content

                # if new_filename contents equal dest_filename contents, then we are done
                if md5sum(new_filename)[0] == md5sum(dest_filename)[0]:
                    return

                # new_filename content and dest_filename content differ

                # so if there is a backup file and if the backup file contents diff from the dest_filename contents,
                # then we rename the dest_filename to then incremented backup_filename (one past the highest
                # existing value)
                backup_filename = next_backup_filename(name=dest_filename)

                os.rename(dest_filename, backup_filename)

                # next we remove the dest_filename then move new_filename to dest_filename
                if os.path.isfile(dest_filename):
                    os.remove(dest_filename)

            shutil.copyfile(new_filename, dest_filename)

        except Exception as ex:
            error("Error rendering template ({file}) - {err}\n{trace}".format(file=src_filename,
                                                                              err=str(ex),
                                                                              trace=traceback.format_exc()))
            error("kwargs:\n{kwargs}".format(kwargs=pformat(kwargs)))
        finally:
            if new_filename is not None:
                if os.path.isfile(new_filename):
                    os.remove(new_filename)
示例#11
0
 def generate():
     """Generate API documents"""
     if doc.doc_errors:
         error(pformat(doc.doc_errors))
     info("{cnt} errors.".format(cnt=len(doc.doc_errors)))
示例#12
0
    # noinspection PyUnresolvedReferences
    from herring.herring_app import task
    # noinspection PyUnresolvedReferences
    from herringlib.venv import VirtualenvInfo
    # noinspection PyUnresolvedReferences
    from herringlib.project_settings import Project
    # noinspection PyUnresolvedReferences
    from herringlib.local_shell import LocalShell
    # noinspection PyUnresolvedReferences
    from herringlib.simple_logger import error, info, warning
    # noinspection PyUnresolvedReferences
    from herringlib.remote_shell import RemoteShell
except ImportError as ex:
    from herringlib.simple_logger import error

    error("Problem importing:  {msg}".format(msg=str(ex)))

__docformat__ = 'restructuredtext en'

# noinspection PyBroadException
try:

    def _dist_wheel_files():
        pattern = "{name}-{version}-*.whl".format(name=Project.base_name, version=Project.version)
        project_wheel_names = [os.path.basename(path) for path in glob(os.path.join(Project.herringfile_dir,
                                                                                    'dist', pattern))]
        dist_wheel_files = []
        for project_wheel_name in project_wheel_names:
            dist_wheel_files.append(os.path.join(Project.herringfile_dir, 'dist', project_wheel_name))
        return dist_wheel_files
示例#13
0
文件: doc.py 项目: royw/herringlib
 def generate_no_api():
     """Generate API documents without the API"""
     global doc_errors
     if doc_errors:
         error(pformat(doc_errors))
         info("{cnt} errors.".format(cnt=len(doc_errors)))