Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add addon flags to kedro new #3081

Merged
merged 99 commits into from
Oct 24, 2023
Merged
Show file tree
Hide file tree
Changes from 85 commits
Commits
Show all changes
99 commits
Select commit Hold shift + click to select a range
3726ed7
Update prompts.yml
SajidAlamQB Aug 30, 2023
592afb5
Update starters.py
SajidAlamQB Aug 31, 2023
dd27d67
add post_gen_project in cookiecutter hooks
SajidAlamQB Sep 4, 2023
ad127d8
add confirmation message for the options selected
SajidAlamQB Sep 4, 2023
868816c
Merge branch 'develop' into feat/add-ons-cli-flow
SajidAlamQB Sep 5, 2023
52e99dd
Update post_gen_project.py
SajidAlamQB Sep 5, 2023
5108223
changes based on review
SajidAlamQB Sep 5, 2023
6cc090c
Merge branch 'develop' into feat/add-ons-cli-flow
lrcouto Sep 7, 2023
a0fe4a2
Lint
Sep 8, 2023
4fb0671
Remove documentation requirements
Sep 11, 2023
c1a1f7d
Remove testing requirements
Sep 11, 2023
ba01bb2
Remove leftover linting requirements
Sep 11, 2023
0f92782
Lint
Sep 11, 2023
bc0c172
Add add-on requirements when an addon is selected
lrcouto Sep 12, 2023
52ddf73
Correct file path
lrcouto Sep 12, 2023
ded026c
Update tests with new default template files number
Sep 12, 2023
f216847
Update tests with add-ons argument
Sep 12, 2023
ee668fd
Make lint
Sep 12, 2023
a500a7a
Lint
Sep 12, 2023
b88f01c
Make tests use all add-ons by default
Sep 12, 2023
fa379a0
Merge branch 'develop' into feat/add-ons-cli-flow
AhdraMeraliQB Sep 12, 2023
f39ebad
Make unit tests use no add-ons by default
Sep 12, 2023
4a4164d
Add installing project dependencies to e2e tests
Sep 12, 2023
ea40e0e
Add linting requirements, organize code
lrcouto Sep 12, 2023
d56cc31
Refactor test for all add on options
Sep 13, 2023
6208edb
Add test to check parsing add-ons
Sep 13, 2023
66c9f36
Add scaffolding for add-ons tests
Sep 13, 2023
58f211f
Change name of test class
Sep 13, 2023
119465d
Correct test names
Sep 13, 2023
5434858
Correct tests directory
Sep 13, 2023
225f26a
Clean up success message
Sep 13, 2023
2f866f7
Merge branch 'develop' into feat/add-ons-cli-flow
lrcouto Sep 13, 2023
06509fd
Fix logging option
Sep 13, 2023
e73fe7e
Update lint add-on logic
Sep 13, 2023
bb4e358
Ensure add-ons message only shows when add-ons are configurable
Sep 13, 2023
1a52a3c
Add requirement checks to tests
lrcouto Sep 14, 2023
51d0c12
Refactor unit tests
Sep 14, 2023
39761d0
Add validation to add ons in config file
Sep 14, 2023
da14a74
Refactor add-ons flow script
lrcouto Sep 18, 2023
0160bbe
Pass through correct repo name in test
Sep 19, 2023
8609597
Merge branch 'develop' into feat/add-ons-cli-flow
AhdraMeraliQB Sep 19, 2023
603fc93
Clean up and clarify text
Sep 19, 2023
aae48cb
Wrap hook script inside main function
Sep 19, 2023
ca6297a
Revert displayed default
Sep 19, 2023
4a9cdcb
Add range validation
Sep 19, 2023
3711567
Add tests for add-on range validation
Sep 19, 2023
e037441
Apply suggestions from code review
AhdraMeraliQB Sep 19, 2023
08567d3
Update kedro/templates/project/hooks/utils.py
AhdraMeraliQB Sep 19, 2023
7fca19e
Apply suggestions from code review
Sep 19, 2023
47d935e
Remove traceback from add-on validation - review suggestion
Sep 19, 2023
e3c7de5
Output add-on names when selected (via CLI)
Sep 19, 2023
fd0dabd
Merge branch 'develop' into feat/add-ons-cli-flow
AhdraMeraliQB Sep 19, 2023
f8b8920
Merge branch 'develop' into feat/add-ons-cli-flow
lrcouto Sep 20, 2023
57cf29c
Revert 47d935e and fix tests
Sep 21, 2023
951015d
Fix test errors
Sep 21, 2023
d280307
Try remove validation
Sep 21, 2023
8a51b26
Add validation back
Sep 21, 2023
abd467f
Merge branch 'develop' into feat/add-ons-cli-flow
AhdraMeraliQB Sep 22, 2023
47d063f
Add config file input validation
Sep 22, 2023
488eca9
Add /site-packages/ to coverage report omit
Sep 22, 2023
c5e3050
Lint
Sep 22, 2023
472a57c
Remove duplicate error message
Sep 22, 2023
e0e5077
Lint
Sep 22, 2023
e89ed0c
Merge develop into feat/add-ons-cli-flow
Sep 22, 2023
86058e1
Add new flag and help string
lrcouto Sep 22, 2023
b5bae5d
Parse addon list from CLI input
lrcouto Sep 25, 2023
e0ac01d
Overwrite addons from prompts with addons from flag
lrcouto Sep 25, 2023
175120a
Remove addons prompt when addons flag is present
lrcouto Sep 25, 2023
7c8f9c5
Use helper function to add addons to config
lrcouto Sep 29, 2023
534866c
Update test to accomodate for new flag
lrcouto Sep 29, 2023
2ae0635
Add new tests for kedro new
lrcouto Oct 3, 2023
fb54190
Fix incorrect docs link
lrcouto Oct 3, 2023
fa92926
Fix another incorrect docs link
lrcouto Oct 3, 2023
9442614
Changes to --addons help string
lrcouto Oct 5, 2023
7095ff2
Fix merge conflics
lrcouto Oct 11, 2023
d07444d
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 11, 2023
91e0c86
Lint
lrcouto Oct 11, 2023
c9a4cb8
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 13, 2023
b79f4a8
Fix formatting on --help string
lrcouto Oct 13, 2023
39b1ded
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 16, 2023
249afe8
Change Addons from CLI test to use correct arguments
lrcouto Oct 16, 2023
791ff2a
Convert addon input strings to number
lrcouto Oct 17, 2023
0f2fd1b
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 19, 2023
0fe4cd4
Fix tests for addon flags
lrcouto Oct 19, 2023
ae8bba6
Lint
lrcouto Oct 19, 2023
1566e02
Clean up project on addons CLI test
lrcouto Oct 19, 2023
de51fb8
Change error message on invalid addon input
lrcouto Oct 20, 2023
e8869a1
Make addon CLI test more specific
lrcouto Oct 20, 2023
59943fd
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 20, 2023
f791781
Clean up prompt display function
lrcouto Oct 20, 2023
5c318ac
Merge branch 'add-addon-flags-to-kedro-new' of github.com:kedro-org/k…
lrcouto Oct 20, 2023
ecf3e3d
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 23, 2023
f95b226
Handle whitespaces and invalid cases
lrcouto Oct 24, 2023
bb998d4
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 24, 2023
82b7642
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 24, 2023
d4b47e5
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 24, 2023
cb9da3c
Add --addons flag to release notes
lrcouto Oct 24, 2023
2b76d90
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 24, 2023
3383e4f
Merge branch 'develop' into add-addon-flags-to-kedro-new
lrcouto Oct 24, 2023
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
90 changes: 57 additions & 33 deletions kedro/framework/cli/starters.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@
import stat
import sys
import tempfile
import warnings
from collections import OrderedDict
from itertools import groupby
from pathlib import Path
Expand All @@ -22,7 +21,6 @@
from attrs import define, field

import kedro
from kedro import KedroDeprecationWarning
from kedro import __version__ as version
from kedro.framework.cli.utils import (
CONTEXT_SETTINGS,
Expand All @@ -38,13 +36,6 @@
TEMPLATE_PATH = KEDRO_PATH / "templates" / "project"
_STARTERS_REPO = "git+https://github.com/kedro-org/kedro-starters.git"

_DEPRECATED_STARTERS = [
"pandas-iris",
"pyspark-iris",
"pyspark",
"standalone-datacatalog",
]


@define(order=True)
class KedroStarterSpec: # noqa: too-few-public-methods
Expand Down Expand Up @@ -101,6 +92,23 @@ class KedroStarterSpec: # noqa: too-few-public-methods
"An optional directory inside the repository where the starter resides."
)

# TODO; Insert actual link to the documentation (Visit: kedro.org/{insert-documentation} to find out more about these add-ons.).
ADDON_ARG_HELP = """
Select which add-ons you'd like to include. By default, none are included.\n

Add-Ons\n
1) Linting: Provides a basic linting setup with Black and Ruff\n
2) Testing: Provides basic testing setup with pytest\n
3) Custom Logging: Provides more logging options\n
4) Documentation: Basic documentation setup with Sphinx\n
5) Data Structure: Provides a directory structure for storing data\n

Example usage:\n
kedro new --addons=lint,test,log,docs,data (or any subset of these options)\n
kedro new --addons=all\n
kedro new --addons=none
"""


# noqa: unused-argument
def _remove_readonly(func: Callable, path: Path, excinfo: tuple): # pragma: no cover
Expand Down Expand Up @@ -163,14 +171,10 @@ def _starter_spec_to_dict(
"""Convert a dictionary of starters spec to a nicely formatted dictionary"""
format_dict: dict[str, dict[str, str]] = {}
for alias, spec in starter_specs.items():
if alias in _DEPRECATED_STARTERS:
key = alias + " (deprecated)"
else:
key = alias
format_dict[key] = {} # Each dictionary represent 1 starter
format_dict[key]["template_path"] = spec.template_path
format_dict[alias] = {} # Each dictionary represent 1 starter
format_dict[alias]["template_path"] = spec.template_path
if spec.directory:
format_dict[key]["directory"] = spec.directory
format_dict[alias]["directory"] = spec.directory
return format_dict


Expand All @@ -191,21 +195,9 @@ def create_cli(): # pragma: no cover
@click.option("--starter", "-s", "starter_alias", help=STARTER_ARG_HELP)
@click.option("--checkout", help=CHECKOUT_ARG_HELP)
@click.option("--directory", help=DIRECTORY_ARG_HELP)
def new(config_path, starter_alias, checkout, directory, **kwargs):
@click.option("--addons", "-a", "selected_addons", help=ADDON_ARG_HELP)
def new(config_path, starter_alias, selected_addons, checkout, directory, **kwargs):
"""Create a new kedro project."""

if starter_alias in _DEPRECATED_STARTERS:
warnings.warn(
f"The starter '{starter_alias}' has been deprecated and will be archived from Kedro 0.19.0.",
KedroDeprecationWarning,
)
click.secho(
"From Kedro 0.19.0, the command `kedro new` will come with the option of interactively selecting add-ons "
"for your project such as linting, testing, custom logging, and more. The selected add-ons will add the "
"basic setup for the utilities selected to your projects.",
fg="green",
)

if checkout and not starter_alias:
raise KedroCliError("Cannot use the --checkout flag without a --starter value.")

Expand Down Expand Up @@ -237,6 +229,11 @@ def new(config_path, starter_alias, checkout, directory, **kwargs):
tmpdir = tempfile.mkdtemp()
cookiecutter_dir = _get_cookiecutter_dir(template_path, checkout, directory, tmpdir)
prompts_required = _get_prompts_required(cookiecutter_dir)

# Remove the prompt asking for add-ons if the user already passed them through CLI.
if selected_addons is not None:
del prompts_required["add_ons"]

# We only need to make cookiecutter_context if interactive prompts are needed.
if not config_path:
cookiecutter_context = _make_cookiecutter_context_for_prompts(cookiecutter_dir)
Expand All @@ -262,6 +259,8 @@ def new(config_path, starter_alias, checkout, directory, **kwargs):
else:
config = _fetch_config_from_user_prompts(prompts_required, cookiecutter_context)

config = _get_addons_from_cli_input(selected_addons, config)

cookiecutter_args = _make_cookiecutter_args(config, checkout, directory)
_create_project(template_path, cookiecutter_args)

Expand All @@ -288,9 +287,6 @@ def list_starters():
sorted_starters_dict = dict(
sorted(sorted_starters_dict.items(), key=lambda x: x == "kedro")
)
warnings.warn(
f"The starters {_DEPRECATED_STARTERS} are deprecated and will be archived in Kedro 0.19.0."
)

for origin, starters_spec in sorted_starters_dict.items():
click.secho(f"\nStarters from {origin}\n", fg="yellow")
Expand All @@ -299,6 +295,34 @@ def list_starters():
)


def _get_addons_from_cli_input(
selected_addons: str, config: dict[str, str]
) -> dict[str, str]:
"""Inserts add-on selection from the CLI input in the project
configuration, if it exists. Replaces add-on strings with the
corresponding prompt number.

Args:
selected_addons: a string containing the value for the --addons flag,
or None in case the flag wasn't used.

Returns:
Configuration for starting a new project, with the selected add-ons
from the `--addons` flag.
"""
string_to_number = {"lint": "1", "test": "2", "log": "3", "docs": "4", "data": "5"}

if selected_addons is not None:
addons = selected_addons.split(",")
for i in range(len(addons)):
addon = addons[i]
if addon in string_to_number:
addons[i] = string_to_number[addon]
config["add_ons"] = ",".join(addons)

return config


def _fetch_config_from_file(config_path: str) -> dict[str, str]:
"""Obtains configuration for a new kedro project non-interactively from a file.

Expand Down
55 changes: 55 additions & 0 deletions tests/framework/cli/test_starters.py
Original file line number Diff line number Diff line change
Expand Up @@ -56,6 +56,24 @@ def _make_cli_prompt_input(
return "\n".join([add_ons, project_name, repo_name, python_package])


def _make_cli_prompt_input_without_addons(
project_name="", repo_name="", python_package=""
):
return "\n".join([project_name, repo_name, python_package])


def _convert_addon_names_to_numbers(selected_addons: str):
string_to_number = {"lint": "1", "test": "2", "log": "3", "docs": "4", "data": "5"}

addons = selected_addons.split(",")
for i in range(len(addons)):
addon = addons[i]
if addon in string_to_number:
addons[i] = string_to_number[addon]

return ",".join(addons)


def _get_expected_files(add_ons: str):
add_ons_template_files = {
"1": 0,
Expand Down Expand Up @@ -933,3 +951,40 @@ def test_invalid_add_ons(self, fake_kedro_cli):
"Please select valid options for add-ons using comma-separated values, ranges, or 'all/none'.\n"
in result.output
)


@pytest.mark.usefixtures("chdir_to_tmp")
class TestAddOnsFromCLI:
@pytest.mark.parametrize(
"add_ons",
[
"lint",
"test",
"log",
"docs",
"data",
"none",
"test,log,docs",
"test,data,lint",
"log,docs,data,test,lint",
"all",
],
)
def test_valid_add_ons(self, fake_kedro_cli, add_ons):
result = CliRunner().invoke(
fake_kedro_cli,
["new", "--addons", add_ons],
input=_make_cli_prompt_input_without_addons(),
)
add_ons = _convert_addon_names_to_numbers(selected_addons=add_ons)
_assert_template_ok(result, add_ons=add_ons)
_assert_requirements_ok(result, add_ons=add_ons)
merelcht marked this conversation as resolved.
Show resolved Hide resolved

def test_invalid_add_ons(self, fake_kedro_cli):
result = CliRunner().invoke(
fake_kedro_cli,
["new", "--addons", "bad_input"],
input=_make_cli_prompt_input_without_addons(),
)

assert result.exit_code != 0
2 changes: 2 additions & 0 deletions tests/tools/test_cli.py
Original file line number Diff line number Diff line change
Expand Up @@ -101,6 +101,8 @@ def test_get_cli_structure_depth(self, mocker, fake_metadata):
"-v",
"--config",
"-c",
"--addons",
"-a",
"--starter",
"-s",
"--checkout",
Expand Down
Loading