def build_package_from_pr_number(gh_token, sdk_id, pr_number, output_folder, *, with_comment=False): """Will clone the given PR branch and vuild the package with the given name.""" con = Github(gh_token) repo = con.get_repo(sdk_id) sdk_pr = repo.get_pull(pr_number) package_names = get_package_names(sdk_pr) absolute_output_folder = Path(output_folder).resolve() with tempfile.TemporaryDirectory() as temp_dir, manage_git_folder( gh_token, Path(temp_dir) / Path("sdk"), sdk_id, pr_number=pr_number ) as sdk_repo_root: for _, package_name in package_names: _LOGGER.debug("Build {}".format(package_name)) execute_simple_command( ["python", "./build_package.py", "--dest", str(absolute_output_folder), package_name], cwd=sdk_repo_root ) _LOGGER.debug("Build finished: {}".format(package_name)) if with_comment: files = [f.name for f in absolute_output_folder.iterdir()] comment_message = None dashboard = DashboardCommentableObject(sdk_pr, "(message created by the CI based on PR content)") try: installation_message = build_installation_message(sdk_pr) download_message = build_download_message(sdk_pr, files) comment_message = installation_message + "\n\n" + download_message dashboard.create_comment(comment_message) except Exception: _LOGGER.critical("Unable to do PR comment:\n%s", comment_message)
def build_package_from_pr_number(gh_token, sdk_id, pr_number, output_folder, *, with_comment=False): """Will clone the given PR branch and vuild the package with the given name.""" con = Github(gh_token) repo = con.get_repo(sdk_id) sdk_pr = repo.get_pull(pr_number) # "get_files" of Github only download the first 300 files. Might not be enough. package_names = {f.filename.split('/')[0] for f in sdk_pr.get_files() if f.filename.startswith("azure")} absolute_output_folder = Path(output_folder).resolve() with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(gh_token, Path(temp_dir) / Path("sdk"), sdk_id, pr_number=pr_number) as sdk_folder: for package_name in package_names: _LOGGER.debug("Build {}".format(package_name)) execute_simple_command( ["python", "./build_package.py", "--dest", str(absolute_output_folder), package_name], cwd=sdk_folder ) _LOGGER.debug("Build finished: {}".format(package_name)) if with_comment: files = [f.name for f in absolute_output_folder.iterdir()] comment_message = None dashboard = DashboardCommentableObject(sdk_pr, "(message created by the CI based on PR content)") try: installation_message = build_installation_message(sdk_pr) download_message = build_download_message(sdk_pr, files) comment_message = installation_message + "\n\n" + download_message dashboard.create_comment(comment_message) except Exception: _LOGGER.critical("Unable to do PR comment:\n%s", comment_message)
def rebase(self, issue, branch=None): if not issue.pull_request: return "Rebase is just supported in PR for now" pr = issue.repository.get_pull(issue.number) branch_name = pr.head.ref branched_sdk_id = pr.head.repo.full_name+'@'+branch_name upstream_url = 'https://github.com/{}.git'.format(pr.base.repo.full_name) upstream_base = pr.base.ref if not branch else branch with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(self.gh_token, Path(temp_dir) / Path("sdk"), branched_sdk_id) as sdk_folder: sdk_repo = Repo(str(sdk_folder)) configure_user(self.gh_token, sdk_repo) upstream = sdk_repo.create_remote('upstream', url=upstream_url) upstream.fetch() msg = sdk_repo.git.rebase('upstream/{}'.format(upstream_base)) _LOGGER.debug(msg) msg = sdk_repo.git.push(force=True) _LOGGER.debug(msg) return "Rebase done and pushed to the branch"
def rebase(self, issue, branch=None): if not issue.pull_request: return "Rebase is just supported in PR for now" pr = issue.repository.get_pull(issue.number) branch_name = pr.head.ref branched_sdk_id = pr.head.repo.full_name + '@' + branch_name upstream_url = 'https://github.com/{}.git'.format( pr.base.repo.full_name) upstream_base = pr.base.ref if not branch else branch with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(self.gh_token, Path(temp_dir) / Path("sdk"), branched_sdk_id) as sdk_folder: sdk_repo = Repo(str(sdk_folder)) configure_user(self.gh_token, sdk_repo) upstream = sdk_repo.create_remote('upstream', url=upstream_url) upstream.fetch() msg = sdk_repo.git.rebase('upstream/{}'.format(upstream_base)) _LOGGER.debug(msg) msg = sdk_repo.git.push(force=True) _LOGGER.debug(msg) return "Rebase done and pushed to the branch"
def update_pr(gh_token, repo_id, pr_number): from github import Github con = Github(gh_token) repo = con.get_repo(repo_id) sdk_pr = repo.get_pull(pr_number) # "get_files" of Github only download the first 300 files. Might not be enough. package_names = {f.filename.split('/')[0] for f in sdk_pr.get_files() if f.filename.startswith("azure")} # Get PR branch to push head_repo = sdk_pr.head.repo.full_name head_branch = sdk_pr.head.ref branched_index = "{}@{}".format(head_repo, head_branch) with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(gh_token, Path(temp_dir) / Path("sdk"), branched_index) as sdk_folder: sdk_repo = Repo(str(sdk_folder)) configure_user(gh_token, sdk_repo) for package_name in package_names: if package_name.endswith("nspkg"): _LOGGER.info("Skip nspkg packages for update PR") continue # Rebuild packaging build_packaging_by_package_name(package_name, sdk_folder, build_conf=True) # Commit that do_commit( sdk_repo, "Packaging update of {}".format(package_name), head_branch, None # Unused ) # Push all commits at once sdk_repo.git.push('origin', head_branch, set_upstream=True)
def test_manage_git_folder(self): github_token = self.oauth_token finished = False # Authorize PermissionError on cleanup try: with tempfile.TemporaryDirectory() as temp_dir, manage_git_folder( github_token, temp_dir, "lmazuel/TestingRepo") as rest_repo: assert (Path(rest_repo) / Path("README.md")).exists() finished = True except (PermissionError, FileNotFoundError): if not finished: raise finished = False # Authorize PermissionError on cleanup try: with tempfile.TemporaryDirectory() as temp_dir, manage_git_folder( github_token, temp_dir, "lmazuel/TestingRepo@lmazuel-patch-1") as rest_repo: assert (Path(rest_repo) / Path("README.md")).exists() assert "lmazuel-patch-1" in str(Repo(rest_repo).active_branch) finished = True except (PermissionError, FileNotFoundError): if not finished: raise finished = False # Authorize PermissionError on cleanup try: with tempfile.TemporaryDirectory() as temp_dir, manage_git_folder( github_token, temp_dir, "lmazuel/TestingRepo", pr_number=1) as rest_repo: assert (Path(rest_repo) / Path("README.md")).exists() with pytest.raises(TypeError) as err: Repo(rest_repo).active_branch assert "HEAD is a detached symbolic reference" in str(err) finished = True except (PermissionError, FileNotFoundError): if not finished: raise
def generate_sdk(sdk_git_id, base_branch_name, autorest_bin=None): """Main method of the the file""" # On Travis, local folder is restapi git folder restapi_git_folder = '.' config = read_config_from_github(sdk_git_id, base_branch_name) global_conf = config["meta"] # No token is provided to clone SDK. Do NOT try to clone a private it will fail. with tempfile.TemporaryDirectory() as temp_dir: clone_dir = Path(temp_dir) / Path( global_conf.get("advanced_options", {}).get("clone_dir", "sdk")) _LOGGER.info("Clone dir will be: %s", clone_dir) with manage_git_folder(None, clone_dir, sdk_git_id + '@' + base_branch_name) as sdk_folder: sdk_repo = Repo(str(sdk_folder)) swagger_files_in_pr = get_files_in_commit(restapi_git_folder) _LOGGER.info("Files in PR: %s ", swagger_files_in_pr) swagger_files_in_pr = get_readme_files_from_file_list( swagger_files_in_pr, restapi_git_folder) _LOGGER.info("Readmes in PR: %s ", swagger_files_in_pr) # Look for configuration in Readme extract_conf_from_readmes(swagger_files_in_pr, restapi_git_folder, sdk_git_id, config) def skip_callback(project, local_conf): if not swagger_files_in_pr: return True # Travis with no files found, always skip markdown_relative_path, optional_relative_paths = get_input_paths( global_conf, local_conf) if swagger_files_in_pr and not ( markdown_relative_path in swagger_files_in_pr or any(input_file in swagger_files_in_pr for input_file in optional_relative_paths)): _LOGGER.info( f"In project {project} no files involved in this PR") return True return False from . import SwaggerToSdkNewCLI SwaggerToSdkNewCLI.build_libraries(config, skip_callback, restapi_git_folder, sdk_repo, temp_dir, autorest_bin) _LOGGER.info("Build SDK finished and cleaned")
def build_package_from_pr_number(gh_token, sdk_id, pr_number, output_folder, *, with_comment=False): """Will clone the given PR branch and vuild the package with the given name.""" con = Github(gh_token) repo = con.get_repo(sdk_id) sdk_pr = repo.get_pull(pr_number) files = [ one_file.filename for one_file in sdk_pr.get_files() if one_file.status not in ['removed'] ] # "get_files" of Github only download the first 300 files. Might not be enough. package_names = {('.', f.split('/')[0]) for f in files if f.startswith("azure")} # Handle the SDK folder as well matches = {_SDK_FOLDER_RE.search(f) for f in files} package_names.update( {match.groups() for match in matches if match is not None}) absolute_output_folder = Path(output_folder).resolve() with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(gh_token, Path(temp_dir) / Path("sdk"), sdk_id, pr_number=pr_number) as sdk_repo_root: for _, package_name in package_names: _LOGGER.debug("Build {}".format(package_name)) execute_simple_command([ "python", "./build_package.py", "--dest", str(absolute_output_folder), package_name ], cwd=sdk_repo_root) _LOGGER.debug("Build finished: {}".format(package_name)) if with_comment: files = [f.name for f in absolute_output_folder.iterdir()] comment_message = None dashboard = DashboardCommentableObject( sdk_pr, "(message created by the CI based on PR content)") try: installation_message = build_installation_message(sdk_pr) download_message = build_download_message(sdk_pr, files) comment_message = installation_message + "\n\n" + download_message dashboard.create_comment(comment_message) except Exception: _LOGGER.critical("Unable to do PR comment:\n%s", comment_message)
def update_pr(gh_token, repo_id, pr_number): from github import Github con = Github(gh_token) repo = con.get_repo(repo_id) sdk_pr = repo.get_pull(pr_number) files = [ one_file.filename for one_file in sdk_pr.get_files() if one_file.status not in ['removed'] ] # "get_files" of Github only download the first 300 files. Might not be enough. package_names = {('.', f.split('/')[0]) for f in files if f.startswith("azure")} # Handle the SDK folder as well matches = {_SDK_FOLDER_RE.search(f) for f in files} package_names.update( {match.groups() for match in matches if match is not None}) # Get PR branch to push head_repo = sdk_pr.head.repo.full_name head_branch = sdk_pr.head.ref branched_index = "{}@{}".format(head_repo, head_branch) _LOGGER.info("Checkout %s", branched_index) with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(gh_token, Path(temp_dir) / Path("sdk"), branched_index) as sdk_repo_root: sdk_repo = Repo(str(sdk_repo_root)) configure_user(gh_token, sdk_repo) for base_folder, package_name in package_names: if package_name.endswith("nspkg"): _LOGGER.info("Skip nspkg packages for update PR") continue # Rebuild packaging _LOGGER.info("Try update package %s from folder %s", package_name, base_folder) build_packaging_by_package_name(package_name, sdk_repo_root / Path(base_folder), build_conf=True) # Commit that do_commit( sdk_repo, "Packaging update of {}".format(package_name), head_branch, None # Unused ) # Push all commits at once sdk_repo.git.push('origin', head_branch, set_upstream=True)
def generate_sdk(sdk_git_id, base_branch_name, autorest_bin=None): """Main method of the the file""" # On Travis, local folder is restapi git folder restapi_git_folder = '.' config = read_config_from_github(sdk_git_id, base_branch_name) global_conf = config["meta"] # No token is provided to clone SDK. Do NOT try to clone a private it will fail. with tempfile.TemporaryDirectory() as temp_dir: clone_dir = Path(temp_dir) / Path(global_conf.get("advanced_options", {}).get("clone_dir", "sdk")) _LOGGER.info("Clone dir will be: %s", clone_dir) with manage_git_folder(None, clone_dir, sdk_git_id+'@'+base_branch_name) as sdk_folder: sdk_repo = Repo(str(sdk_folder)) swagger_files_in_pr = get_files_in_commit(restapi_git_folder) _LOGGER.info("Files in PR: %s ", swagger_files_in_pr) swagger_files_in_pr = get_readme_files_from_file_list(swagger_files_in_pr, restapi_git_folder) _LOGGER.info("Readmes in PR: %s ", swagger_files_in_pr) # Look for configuration in Readme extract_conf_from_readmes(swagger_files_in_pr, restapi_git_folder, sdk_git_id, config) def skip_callback(project, local_conf): if not swagger_files_in_pr: return True # Travis with no files found, always skip markdown_relative_path, optional_relative_paths = get_input_paths(global_conf, local_conf) if swagger_files_in_pr and not ( markdown_relative_path in swagger_files_in_pr or any(input_file in swagger_files_in_pr for input_file in optional_relative_paths)): _LOGGER.info(f"In project {project} no files involved in this PR") return True return False from . import SwaggerToSdkNewCLI SwaggerToSdkNewCLI.build_libraries(config, skip_callback, restapi_git_folder, sdk_repo, temp_dir, autorest_bin) _LOGGER.info("Build SDK finished and cleaned")
def git(self, issue, *git_parameters): if not issue.pull_request: return "Rebase is just supported in PR for now" pr_obj = issue.repository.get_pull(issue.number) branch_name = pr_obj.head.ref branched_sdk_id = pr_obj.head.repo.full_name+'@'+branch_name with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(self.gh_token, Path(temp_dir) / Path("sdk"), branched_sdk_id) as sdk_folder: sdk_repo = Repo(str(sdk_folder)) configure_user(self.gh_token, sdk_repo) command = getattr(sdk_repo.git, git_parameters[0]) initial_answer = command(*git_parameters[1:]) _LOGGER.debug(initial_answer) msg = sdk_repo.git.push(force=True) _LOGGER.debug(msg) return "```shell\n"+initial_answer+"\n```"
def git(self, issue, *git_parameters): if not issue.pull_request: return "Rebase is just supported in PR for now" pr_obj = issue.repository.get_pull(issue.number) branch_name = pr_obj.head.ref branched_sdk_id = pr_obj.head.repo.full_name + '@' + branch_name with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(self.gh_token, Path(temp_dir) / Path("sdk"), branched_sdk_id) as sdk_folder: sdk_repo = Repo(str(sdk_folder)) configure_user(self.gh_token, sdk_repo) command = getattr(sdk_repo.git, git_parameters[0]) initial_answer = command(*git_parameters[1:]) _LOGGER.debug(initial_answer) msg = sdk_repo.git.push(force=True) _LOGGER.debug(msg) return "```shell\n" + initial_answer + "\n```"
def rebuild(self, issue, project_pattern): if not issue.pull_request: return "Rebuild is just supported in PR for now" sdkid = issue.repository.full_name pr = issue.repository.get_pull(issue.number) new_comment = issue.create_comment("Working on generating {} for you!!!".format(project_pattern)) config_path = CONFIG_FILE message = "Rebuild by "+issue.html_url autorest_bin = None branch_name = pr.head.ref branched_sdk_id = pr.head.repo.full_name+'@'+branch_name if project_pattern.startswith("https://"): link = GithubLink.from_string(project_pattern) link = link.as_raw_link() # Ensure this is a raw link. rest_api_id = link.gitid rest_api_branch = link.branch_or_commit token = link.token if link.token else self.gh_token path = link.path else: rest_api_id = "Azure/azure-rest-api-specs" rest_api_branch = "master" token = self.gh_token path = None # Not such notion of path here, since it's inside SwaggerToSdk conf branched_rest_api_id = rest_api_id + "@" + rest_api_branch config = read_config_from_github(pr.head.repo.full_name, branch_name, token) with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(token, Path(temp_dir) / Path("rest"), branched_rest_api_id) as restapi_git_folder, \ manage_git_folder(self.gh_token, Path(temp_dir) / Path("sdk"), branched_sdk_id) as sdk_folder: sdk_repo = Repo(str(sdk_folder)) configure_user(self.gh_token, sdk_repo) if path: # Assume this is a Readme path config["projects"] = {} # Wipe out everything build_swaggertosdk_conf_from_json_readme(path, sdkid, config, base_folder=restapi_git_folder) skip_callback = lambda x, y: False else: def skip_callback(project, local_conf): del local_conf # Unused if not project.startswith(project_pattern): return True return False from swaggertosdk import SwaggerToSdkNewCLI SwaggerToSdkNewCLI.build_libraries(config, skip_callback, restapi_git_folder, sdk_repo, temp_dir, autorest_bin) new_comment.edit("End of generation, doing commit") commit_sha = do_commit(sdk_repo, message, branch_name, "") if commit_sha: new_comment.edit("Pushing") sdk_repo.git.push('origin', branch_name, set_upstream=True) new_comment.delete() else: new_comment.delete() return "Nothing to rebuild, this PR is up to date" _LOGGER.info("Build SDK finished and cleaned") return "Build SDK finished and cleaned"
def generate_sdk_from_git_object(git_object, branch_name, restapi_git_id, sdk_git_id, base_branch_names, *, fallback_base_branch_name="master", sdk_tag=None): """Generate SDK from a commit or a PR object. git_object is the initial commit/PR from the RestAPI repo. If git_object is a PR, prefer to checkout Github PR "merge_commit_sha" restapi_git_id explains where to clone the repo. sdk_git_id explains where to push the commit. sdk_tag explains what is the tag used in the Readme for the swagger-to-sdk section. If not provided, use sdk_git_id. branch_name is the expected branch name in the SDK repo. - If this branch exists, use it. - If not, use the base branch to create that branch (base branch is where I intend to do my PR) - If base_branch_names is not provided, use fallback_base_branch_name as base - If this base branch is provided and does not exists, create this base branch first using fallback_base_branch_name (this one is required to exist) WARNING: This method might push to "branch_name" and "base_branch_name". No push will be made to "fallback_base_branch_name" """ gh_token = os.environ["GH_TOKEN"] message_template = DEFAULT_COMMIT_MESSAGE autorest_bin = None if sdk_tag is None: sdk_tag = sdk_git_id try: # Checkout the sha if commit obj branched_rest_api_id = restapi_git_id+'@'+git_object.sha pr_number = None except (AttributeError, TypeError): # This is a PR, don't clone the fork but "base" repo and PR magic commit if git_object.merge_commit_sha: branched_rest_api_id = git_object.base.repo.full_name+'@'+git_object.merge_commit_sha else: branched_rest_api_id = git_object.base.repo.full_name pr_number = git_object.number # Always clone SDK from fallback branch that is required to exist branched_sdk_git_id = sdk_git_id+'@'+fallback_base_branch_name # I don't know if the destination branch exists, try until it works config = None branch_list = base_branch_names + [branch_name] + [fallback_base_branch_name] for branch in branch_list: try: config = read_config_from_github(sdk_git_id, branch, gh_token) except Exception: pass else: break if config is None: raise ValueError("Unable to locate configuration in {}".format(branch_list)) global_conf = config["meta"] # If PR is only about a language that this conf can't handle, skip fast if not this_conf_will_generate_for_this_pr(git_object, global_conf): _LOGGER.info("Skipping this job based on conf not impacted by Git object") return with tempfile.TemporaryDirectory() as temp_dir: clone_dir = Path(temp_dir) / Path(global_conf.get("advanced_options", {}).get("clone_dir", "sdk")) _LOGGER.info("Clone dir will be: %s", clone_dir) with manage_git_folder(gh_token, Path(temp_dir) / Path("rest"), branched_rest_api_id, pr_number=pr_number) as restapi_git_folder, \ manage_git_folder(gh_token, clone_dir, branched_sdk_git_id) as sdk_folder: readme_files_infered = get_readme_files_from_git_object(git_object, restapi_git_folder) _LOGGER.info("Readmes files infered from PR: %s ", readme_files_infered) if not readme_files_infered: _LOGGER.info("No Readme in PR, quit") return # SDK part sdk_repo = Repo(str(sdk_folder)) for base_branch in base_branch_names: _LOGGER.info('Checkout and create %s', base_branch) checkout_and_create_branch(sdk_repo, base_branch) _LOGGER.info('Try to checkout destination branch %s', branch_name) try: sdk_repo.git.checkout(branch_name) _LOGGER.info('The branch exists.') except GitCommandError: _LOGGER.info('Destination branch does not exists') # Will be created by do_commit configure_user(gh_token, sdk_repo) # Look for configuration in Readme _LOGGER.info('Extract conf from Readmes for target: %s', sdk_git_id) extract_conf_from_readmes(readme_files_infered, restapi_git_folder, sdk_tag, config) _LOGGER.info('End of extraction') def skip_callback(project, local_conf): # We know "project" is based on Path in "readme_files_infered" if Path(project) in readme_files_infered: return False # Might be a regular project markdown_relative_path, optional_relative_paths = get_input_paths(global_conf, local_conf) if not ( markdown_relative_path in readme_files_infered or any(input_file in readme_files_infered for input_file in optional_relative_paths)): _LOGGER.info(f"In project {project} no files involved in this commit") return True return False build_libraries(config, skip_callback, restapi_git_folder, sdk_repo, temp_dir, autorest_bin) try: commit_for_sha = git_object.commit # Commit except AttributeError: commit_for_sha = list(git_object.get_commits())[-1].commit # PR message = message_template + "\n\n" + commit_for_sha.message commit_sha = do_commit(sdk_repo, message, branch_name, commit_for_sha.sha) if commit_sha: for base_branch in base_branch_names: sdk_repo.git.push('origin', base_branch, set_upstream=True) sdk_repo.git.push('origin', branch_name, set_upstream=True) return "https://github.com/{}/commit/{}".format(sdk_git_id, commit_sha)
def generate_sdk_from_git_object(git_object, branch_name, restapi_git_id, sdk_git_id, base_branch_names, *, fallback_base_branch_name="master", sdk_tag=None): """Generate SDK from a commit or a PR object. git_object is the initial commit/PR from the RestAPI repo. If git_object is a PR, prefer to checkout Github PR "merge_commit_sha" restapi_git_id explains where to clone the repo. sdk_git_id explains where to push the commit. sdk_tag explains what is the tag used in the Readme for the swagger-to-sdk section. If not provided, use sdk_git_id. branch_name is the expected branch name in the SDK repo. - If this branch exists, use it. - If not, use the base branch to create that branch (base branch is where I intend to do my PR) - If base_branch_names is not provided, use fallback_base_branch_name as base - If this base branch is provided and does not exists, create this base branch first using fallback_base_branch_name (this one is required to exist) WARNING: This method might push to "branch_name" and "base_branch_name". No push will be made to "fallback_base_branch_name" """ gh_token = os.environ["GH_TOKEN"] message_template = DEFAULT_COMMIT_MESSAGE autorest_bin = None if sdk_tag is None: sdk_tag = sdk_git_id try: # Checkout the sha if commit obj branched_rest_api_id = restapi_git_id + '@' + git_object.sha pr_number = None except ( AttributeError, TypeError ): # This is a PR, don't clone the fork but "base" repo and PR magic commit if git_object.merge_commit_sha: branched_rest_api_id = git_object.base.repo.full_name + '@' + git_object.merge_commit_sha else: branched_rest_api_id = git_object.base.repo.full_name pr_number = git_object.number # Always clone SDK from fallback branch that is required to exist branched_sdk_git_id = sdk_git_id + '@' + fallback_base_branch_name # I don't know if the destination branch exists, try until it works config = None branch_list = base_branch_names + [branch_name ] + [fallback_base_branch_name] for branch in branch_list: try: config = read_config_from_github(sdk_git_id, branch, gh_token) except Exception: pass else: break if config is None: raise ValueError( "Unable to locate configuration in {}".format(branch_list)) global_conf = config["meta"] # If PR is only about a language that this conf can't handle, skip fast if not this_conf_will_generate_for_this_pr(git_object, global_conf): _LOGGER.info( "Skipping this job based on conf not impacted by Git object") return with tempfile.TemporaryDirectory() as temp_dir: clone_dir = Path(temp_dir) / Path( global_conf.get("advanced_options", {}).get("clone_dir", "sdk")) _LOGGER.info("Clone dir will be: %s", clone_dir) with manage_git_folder(gh_token, Path(temp_dir) / Path("rest"), branched_rest_api_id, pr_number=pr_number) as restapi_git_folder, \ manage_git_folder(gh_token, clone_dir, branched_sdk_git_id) as sdk_folder: readme_files_infered = get_readme_files_from_git_object( git_object, restapi_git_folder) _LOGGER.info("Readmes files infered from PR: %s ", readme_files_infered) if not readme_files_infered: _LOGGER.info("No Readme in PR, quit") return # SDK part sdk_repo = Repo(str(sdk_folder)) for base_branch in base_branch_names: _LOGGER.info('Checkout and create %s', base_branch) checkout_and_create_branch(sdk_repo, base_branch) _LOGGER.info('Try to checkout destination branch %s', branch_name) try: sdk_repo.git.checkout(branch_name) _LOGGER.info('The branch exists.') except GitCommandError: _LOGGER.info('Destination branch does not exists') # Will be created by do_commit configure_user(gh_token, sdk_repo) # Look for configuration in Readme _LOGGER.info('Extract conf from Readmes for target: %s', sdk_git_id) extract_conf_from_readmes(readme_files_infered, restapi_git_folder, sdk_tag, config) _LOGGER.info('End of extraction') def skip_callback(project, local_conf): # We know "project" is based on Path in "readme_files_infered" if Path(project) in readme_files_infered: return False # Might be a regular project markdown_relative_path, optional_relative_paths = get_input_paths( global_conf, local_conf) if not (markdown_relative_path in readme_files_infered or any(input_file in readme_files_infered for input_file in optional_relative_paths)): _LOGGER.info( f"In project {project} no files involved in this commit" ) return True return False build_libraries(config, skip_callback, restapi_git_folder, sdk_repo, temp_dir, autorest_bin) try: commit_for_sha = git_object.commit # Commit except AttributeError: commit_for_sha = list( git_object.get_commits())[-1].commit # PR message = message_template + "\n\n" + commit_for_sha.message commit_sha = do_commit(sdk_repo, message, branch_name, commit_for_sha.sha) if commit_sha: for base_branch in base_branch_names: sdk_repo.git.push('origin', base_branch, set_upstream=True) sdk_repo.git.push('origin', branch_name, set_upstream=True) return "https://github.com/{}/commit/{}".format( sdk_git_id, commit_sha)
def rebuild(self, issue, project_pattern): if not issue.pull_request: return "Rebuild is just supported in PR for now" sdkid = issue.repository.full_name pr = issue.repository.get_pull(issue.number) new_comment = issue.create_comment( "Working on generating {} for you!!!".format(project_pattern)) config_path = CONFIG_FILE message = "Rebuild by " + issue.html_url autorest_bin = None branch_name = pr.head.ref branched_sdk_id = pr.head.repo.full_name + '@' + branch_name if project_pattern.startswith("https://"): link = GithubLink.from_string(project_pattern) link = link.as_raw_link() # Ensure this is a raw link. rest_api_id = link.gitid rest_api_branch = link.branch_or_commit token = link.token if link.token else self.gh_token path = link.path else: rest_api_id = "Azure/azure-rest-api-specs" rest_api_branch = "master" token = self.gh_token path = None # Not such notion of path here, since it's inside SwaggerToSdk conf branched_rest_api_id = rest_api_id + "@" + rest_api_branch config = read_config_from_github(pr.head.repo.full_name, branch_name, token) with tempfile.TemporaryDirectory() as temp_dir, \ manage_git_folder(token, Path(temp_dir) / Path("rest"), branched_rest_api_id) as restapi_git_folder, \ manage_git_folder(self.gh_token, Path(temp_dir) / Path("sdk"), branched_sdk_id) as sdk_folder: sdk_repo = Repo(str(sdk_folder)) configure_user(self.gh_token, sdk_repo) if path: # Assume this is a Readme path config["projects"] = {} # Wipe out everything build_swaggertosdk_conf_from_json_readme( path, sdkid, config, base_folder=restapi_git_folder) skip_callback = lambda x, y: False else: def skip_callback(project, local_conf): del local_conf # Unused if not project.startswith(project_pattern): return True return False from swaggertosdk import SwaggerToSdkNewCLI SwaggerToSdkNewCLI.build_libraries(config, skip_callback, restapi_git_folder, sdk_repo, temp_dir, autorest_bin) new_comment.edit("End of generation, doing commit") commit_sha = do_commit(sdk_repo, message, branch_name, "") if commit_sha: new_comment.edit("Pushing") sdk_repo.git.push('origin', branch_name, set_upstream=True) new_comment.delete() else: new_comment.delete() return "Nothing to rebuild, this PR is up to date" _LOGGER.info("Build SDK finished and cleaned") return "Build SDK finished and cleaned"