2
0
mirror of https://github.com/frappe/bench.git synced 2025-01-10 00:37:51 +00:00

refactor: bench get-app

* Added app dependencies resolving using `required_apps`
* Simplified workflow + docstring to explain what's goin on xD
* Get rid of redundant restart_bench kwarg from get_app
This commit is contained in:
Gavin D'souza 2021-10-20 19:34:00 +05:30
parent 1865eeeb6d
commit dafddaef6d

View File

@ -216,59 +216,81 @@ def get_bench_name(git_url, bench_path):
return os.path.join(bench_path, f"{guessed_app_name}-bench")
def get_app(git_url, branch=None, bench_path='.', skip_assets=False, verbose=False, restart_bench=True, overwrite=False):
import shutil
def setup_app_dependencies(repo_name, bench_path='.', branch=None):
# branch kwarg is somewhat of a hack here; since we're assuming the same branches for all apps
# for eg: if you're installing erpnext@develop, you'll want frappe@develop and healthcare@develop too
import glob
if not is_bench_directory(bench_path):
bench_name = get_bench_name(git_url, bench_path)
from bench.commands.make import init
apps_path = os.path.join(os.path.abspath(bench_path), 'apps')
files = glob.glob(os.path.join(apps_path, repo_name, '**', 'hooks.py'))
click.get_current_context().invoke(init, path=bench_name)
bench_path = bench_name
if files:
lines = [x for x in open(files[0]).read().split('\n') if x.strip().startswith('required_apps')]
if lines:
required_apps = eval(lines[0].strip('required_apps').strip().lstrip('=').strip())
# TODO: when the time comes, add version check here
for app in required_apps:
if app not in get_apps(bench_path=bench_path):
get_app(app, bench_path=bench_path, branch=branch)
if not os.path.exists(git_url):
app = App(git_url)
def get_app(git_url, branch=None, bench_path='.', skip_assets=False, verbose=False, overwrite=False):
"""bench get-app clones a Frappe App from remote (GitHub or any other git server),
and installs it on the current bench. This also resolves dependencies based on the
apps' required_apps defined in the hooks.py file.
If the bench_path is not a bench directory, a new bench is created named using the
git_url parameter.
"""
app = App(git_url, branch=branch)
git_url = app.url
repo_name = app.repo
shallow_clone = '--depth 1' if check_git_for_shallow_clone() else ''
branch = f'--branch {app.tag}' if app.tag else ''
branch = app.tag
else:
git_url = os.path.abspath(git_url)
_, repo_name = os.path.split(git_url)
shallow_clone = ''
branch = f'--branch {branch}' if branch else ''
if not is_bench_directory(bench_path):
bench_path = get_bench_name(git_url, bench_path)
from bench.commands.make import init
click.get_current_context().invoke(init, path=bench_path, frappe_branch=branch)
cloned_path = os.path.join(bench_path, 'apps', repo_name)
dir_already_exists = os.path.isdir(cloned_path)
to_clone = not dir_already_exists
to_resolve_dependencies = True
to_install = True
if os.path.isdir(cloned_path):
if dir_already_exists:
# application directory already exists
# prompt user to overwrite it
if overwrite or click.confirm(f'''A directory for the application "{repo_name}" already exists.
Do you want to continue and overwrite it?'''):
import shutil
shutil.rmtree(cloned_path)
to_clone = True
elif click.confirm('''Do you want to reinstall the existing application?''', abort=True):
app_name = get_app_name(bench_path, repo_name)
install_app(
app=app_name, bench_path=bench_path, verbose=verbose, skip_assets=skip_assets
)
sys.exit()
pass
print(f'\n{color.yellow}Getting {repo_name}{color.nc}')
logger.log(f'Getting app {repo_name}')
if to_clone:
fetch_txt = f"Getting {repo_name}"
click.secho(fetch_txt, fg="yellow")
logger.log(fetch_txt)
git_branch = f'--branch {app.tag}' if app.tag else ''
shallow_clone = '--depth 1' if check_git_for_shallow_clone() else ''
exec_cmd(
f"git clone {git_url} {branch} {shallow_clone} --origin upstream",
f"git clone {git_url} {git_branch} {shallow_clone} --origin upstream",
cwd=os.path.join(bench_path, 'apps')
)
if to_resolve_dependencies:
setup_app_dependencies(
repo_name=repo_name, bench_path=bench_path, branch=branch
)
if to_install:
app_name = get_app_name(bench_path, repo_name)
install_app(
app=app_name, bench_path=bench_path, verbose=verbose, skip_assets=skip_assets
)
def get_app_name(bench_path, repo_name):
app_name = None
apps_path = os.path.join(os.path.abspath(bench_path), 'apps')