# Path: src/gwf/backends/base.py
# class Backend:
#     """Base class for backends."""
# 
#     option_defaults = {}
#     log_manager = FileLogManager()
# 
#     @classmethod
#     def list(cls):
#         """Return the names of all registered backends."""
#         return set(_load_backends().keys())
# 
#     @classmethod
#     def from_name(cls, name):
#         """Return backend class for the backend given by `name`.
# 
#         Returns the backend class registered with `name`. Note that the *class*
#         is returned, not the instance, since not all uses requires
#         initialization of the backend (e.g. accessing the backends' log
#         manager), and initialization of the backend may be expensive.
# 
#         :arg str name: Path to a workflow file, optionally specifying a
#             workflow object in that file.
#         """
#         return _load_backends()[name]
# 
#     @classmethod
#     def from_config(cls, config):
#         """Return backend class for the backend specified by `config`.
# 
#         See :func:`Backend.from_name` for further information."""
#         return cls.from_name(config["backend"])
# 
#     def __enter__(self):
#         return self
# 
#     def __exit__(self, exc_type, exc_val, exc_tb):
#         self.close()
# 
#     def status(self, target):
#         """Return the status of `target`.
# 
#         :param gwf.Target target: The target to return the status of.
#         :return gwf.backends.Status: Status of `target`.
#         """
# 
#     def submit_full(self, target, dependencies):
#         """Prepare and submit `target` with `dependencies`.
# 
#         Will prepare the target for submission by injecting option defaults
#         from the backend, check for unsupported options, and removing options
#         with a `None` value.
# 
#         This is the primary way to submit a target. Do not call
#         :func:`submit` directly, unless you want to manually deal with with
#         injection of option defaults.
#         """
#         new_options = dict(self.option_defaults)
#         new_options.update(target.options)
# 
#         for option_name, option_value in list(new_options.items()):
#             if option_name not in self.option_defaults.keys():
#                 logger.warning(
#                     "Option '%s' used in '%s' is not supported by backend. Ignored.",
#                     option_name,
#                     target.name,
#                 )
#                 del new_options[option_name]
#             elif option_value is None:
#                 del new_options[option_name]
#         target.options = new_options
# 
#         self.submit(target, dependencies)
# 
#     def submit(self, target, dependencies):
#         """Submit `target` with `dependencies`.
# 
#         This method must submit the `target` and return immediately. That is,
#         the method must not block while waiting for the target to complete.
# 
#         :param gwf.Target target:
#             The target to submit.
#         :param dependencies:
#             An iterable of :class:`gwf.Target` objects that `target` depends on
#             and that have already been submitted to the backend.
#         """
# 
#     def cancel(self, target):
#         """Cancel `target`.
# 
#         :param gwf.Target target:
#             The target to cancel.
#         :raises gwf.exception.TargetError:
#             If the target does not exist in the workflow.
#         """
# 
#     @classmethod
#     def logs(cls, target, stderr=False):
#         """Return log files for a target.
# 
#         If the backend cannot return logs a
#         :class:`~gwf.exceptions.NoLogFoundError` is raised.
# 
#         By default standard output (stdout) is returned. If `stderr=True`
#         standard error will be returned instead.
# 
#         :param gwf.Target target:
#             Target to return logs for.
#         :param bool stderr:
#             default: False. If true, return standard error.
#         :return:
#             A file-like object. The user is responsible for closing the
#             returned file(s) after use.
#         :raises gwf.exceptions.NoLogFoundError:
#             if the backend could not find a log for the given target.
#         """
#         if stderr:
#             return cls.log_manager.open_stderr(target)
#         return cls.log_manager.open_stdout(target)
# 
#     def close(self):
#         """Close the backend.
# 
#         Called when the backend is no longer needed and should close all
#         resources (open files, connections) used by the backend.
#         """
# 
# Path: src/gwf/conf.py
# def config_from_path(path):
#     return FileConfig.load(path, defaults=CONFIG_DEFAULTS)


from pathlib import Path
from ..backends import Backend
from ..conf import config_from_path
import click
    max_width = max(len(line) for line in banner.splitlines())
    indent = int(width / 2 - max_width / 2)
    centered_banner = "\n".join((" " * indent) + line for line in banner.splitlines())

    click.echo()
    click.secho(centered_banner, fg="blue")
    click.echo()
    click.echo("Welcome!".center(width))
    click.echo()
    click.echo()

    project_dir = click.prompt(
        "Where do you want your project?",
        default=Path("."),
        value_proc=lambda x: Path(x),
    )
    backend = click.prompt(
        "Which backend do you want to use?",
        default="local",
        type=click.Choice(Backend.list()),
        show_choices=True,
    )

    click.echo("Generating project skeleton...")
    project_dir.mkdir(parents=True, exist_ok=True)
    project_dir.joinpath("workflow.py").write_text(workflow_template)
    project_dir.joinpath("templates.py").touch()

    click.echo("Setting project configuration...")


# Path: src/gwf/backends/base.py
# class Backend:
#     """Base class for backends."""
# 
#     option_defaults = {}
#     log_manager = FileLogManager()
# 
#     @classmethod
#     def list(cls):
#         """Return the names of all registered backends."""
#         return set(_load_backends().keys())
# 
#     @classmethod
#     def from_name(cls, name):
#         """Return backend class for the backend given by `name`.
# 
#         Returns the backend class registered with `name`. Note that the *class*
#         is returned, not the instance, since not all uses requires
#         initialization of the backend (e.g. accessing the backends' log
#         manager), and initialization of the backend may be expensive.
# 
#         :arg str name: Path to a workflow file, optionally specifying a
#             workflow object in that file.
#         """
#         return _load_backends()[name]
# 
#     @classmethod
#     def from_config(cls, config):
#         """Return backend class for the backend specified by `config`.
# 
#         See :func:`Backend.from_name` for further information."""
#         return cls.from_name(config["backend"])
# 
#     def __enter__(self):
#         return self
# 
#     def __exit__(self, exc_type, exc_val, exc_tb):
#         self.close()
# 
#     def status(self, target):
#         """Return the status of `target`.
# 
#         :param gwf.Target target: The target to return the status of.
#         :return gwf.backends.Status: Status of `target`.
#         """
# 
#     def submit_full(self, target, dependencies):
#         """Prepare and submit `target` with `dependencies`.
# 
#         Will prepare the target for submission by injecting option defaults
#         from the backend, check for unsupported options, and removing options
#         with a `None` value.
# 
#         This is the primary way to submit a target. Do not call
#         :func:`submit` directly, unless you want to manually deal with with
#         injection of option defaults.
#         """
#         new_options = dict(self.option_defaults)
#         new_options.update(target.options)
# 
#         for option_name, option_value in list(new_options.items()):
#             if option_name not in self.option_defaults.keys():
#                 logger.warning(
#                     "Option '%s' used in '%s' is not supported by backend. Ignored.",
#                     option_name,
#                     target.name,
#                 )
#                 del new_options[option_name]
#             elif option_value is None:
#                 del new_options[option_name]
#         target.options = new_options
# 
#         self.submit(target, dependencies)
# 
#     def submit(self, target, dependencies):
#         """Submit `target` with `dependencies`.
# 
#         This method must submit the `target` and return immediately. That is,
#         the method must not block while waiting for the target to complete.
# 
#         :param gwf.Target target:
#             The target to submit.
#         :param dependencies:
#             An iterable of :class:`gwf.Target` objects that `target` depends on
#             and that have already been submitted to the backend.
#         """
# 
#     def cancel(self, target):
#         """Cancel `target`.
# 
#         :param gwf.Target target:
#             The target to cancel.
#         :raises gwf.exception.TargetError:
#             If the target does not exist in the workflow.
#         """
# 
#     @classmethod
#     def logs(cls, target, stderr=False):
#         """Return log files for a target.
# 
#         If the backend cannot return logs a
#         :class:`~gwf.exceptions.NoLogFoundError` is raised.
# 
#         By default standard output (stdout) is returned. If `stderr=True`
#         standard error will be returned instead.
# 
#         :param gwf.Target target:
#             Target to return logs for.
#         :param bool stderr:
#             default: False. If true, return standard error.
#         :return:
#             A file-like object. The user is responsible for closing the
#             returned file(s) after use.
#         :raises gwf.exceptions.NoLogFoundError:
#             if the backend could not find a log for the given target.
#         """
#         if stderr:
#             return cls.log_manager.open_stderr(target)
#         return cls.log_manager.open_stdout(target)
# 
#     def close(self):
#         """Close the backend.
# 
#         Called when the backend is no longer needed and should close all
#         resources (open files, connections) used by the backend.
#         """
# 
# Path: src/gwf/conf.py
# def config_from_path(path):
#     return FileConfig.load(path, defaults=CONFIG_DEFAULTS)


# Path: src/gwf/plugins/init.py
from pathlib import Path
from ..backends import Backend
from ..conf import config_from_path
import click

    max_width = max(len(line) for line in banner.splitlines())
    indent = int(width / 2 - max_width / 2)
    centered_banner = "\n".join((" " * indent) + line for line in banner.splitlines())

    click.echo()
    click.secho(centered_banner, fg="blue")
    click.echo()
    click.echo("Welcome!".center(width))
    click.echo()
    click.echo()

    project_dir = click.prompt(
        "Where do you want your project?",
        default=Path("."),
        value_proc=lambda x: Path(x),
    )
    backend = click.prompt(
        "Which backend do you want to use?",
        default="local",
        type=click.Choice(Backend.list()),
        show_choices=True,
    )

    click.echo("Generating project skeleton...")
    project_dir.mkdir(parents=True, exist_ok=True)
    project_dir.joinpath("workflow.py").write_text(workflow_template)
    project_dir.joinpath("templates.py").touch()

    click.echo("Setting project configuration...")


    config = config_from_path(project_dir.joinpath(".gwfconf.json"))