blog:2022:0428_nervproj_standalone_py_env

NervProj: support for dedicated python env

I'm just about to start working on a new large python project, and I would like to use my NervProj to handle the project management part. But the proble now is that I still need to be able to run that new project completely independently from NervProj itself.

So this means I should setup a dedicated python environment in this kind of sub project. Let's see here how we should proceed step by step.

  • So let's say I'm working on a project called “my_project”, and with code name “myp”.
  • My current “regular” process is to do the following:
    • Create the project repository on my gitlab server (say in sub path /my_group/my_project)
    • Then add that project in the master nervproject.config.json file:
      {
        "projects": [
         {
            "names": ["my_project", "myp"],
            "repository_url": "ssh://git@gitlab.nervtech.org:22002/my_group/my_project.git"
          }
        ]
      }
    • Then I checkout the project:
      $ cd /cygdrive/d/Projects
      $ nvp -p myp git clone
    • And finally I perform the project init stage:
      $ nvp -p myp admin init
      2022/04/27 14:03:26 [nvp.components.admin] INFO: No change in C:\Users\kenshin\AppData\Roaming\Code\User\settings.json
      2022/04/27 14:03:26 [nvp.components.admin] INFO: Wrtting updated vscode settings in D:\Projects\my_project\.vscode\settings.json
      2022/04/27 14:03:26 [nvp.components.admin] INFO: Writting python env file D:\Projects\my_project\.vs_env
      2022/04/27 14:03:26 [nvp.components.admin] INFO: Writting editor config file D:\Projects\my_project\.editorconfig
      2022/04/27 14:03:26 [nvp.components.admin] INFO: Writting .gitignore file D:\Projects\my_project\.gitignore
      2022/04/27 14:03:26 [nvp.components.admin] INFO: Writting .gitattributes file D:\Projects\my_project\.gitattributes
      2022/04/27 14:03:26 [nvp.components.admin] INFO: Writting nvp_config.json file D:\Projects\my_project\nvp_config.json
      2022/04/27 14:03:26 [nvp.components.admin] INFO: Writting nvp_plug.py file D:\Projects\my_project\nvp_plug.py
      2022/04/27 14:03:26 [nvp.components.admin] INFO: Adding pull section in git config.
  • ⇒ I think it is in the init command above that I should introduce the required updates:
  • I need a flag to disable the deployment of the NVP plugin files (nvp_config.json/nvp_plug.py) ? Or maybe not: that is not really important for now so let's not do it.
  • I need to add a flag to deploy the python packages such as:
    $ nvp -p myp admin init --with-py-env
  • Note also using the short flag version:
    $ nvp -p myp admin init -p
  • And so I've started to update the init command with some special handling whena python env deployment is requested:
            ignore_elems = []
    
            if with_py:
                # We deploy the python packages:
                dest_dir = self.get_path(proj_dir, "tools", "packages")
                self.make_folder(dest_dir)
                # get the python version on windows:
                py_vers = {}
                sevenzip_vers = {}
    
                for plat_name in ["windows", "linux"]:
                    for el in self.config[f'{plat_name}_tools']:
                        if el["name"] == 'python':
                            py_vers[plat_name] = el["version"]
                        if el["name"] == '7zip':
                            sevenzip_vers[plat_name] = el["version"]
    
                for plat_name, py_version in py_vers.items():
                    for ext in [".7z", ".tar.xz"]:
                        file_name = f"python-{py_version}-{plat_name}{ext}"
                        src_file = self.get_path(self.ctx.get_root_dir(), "tools", "packages", file_name)
                        dst_file = self.get_path(dest_dir, file_name)
                        if self.file_exists(src_file) and not self.file_exists(dst_file):
                            logger.info("Adding package file %s", dst_file)
                            self.copy_file(src_file, dst_file)
    
                # Next, for the windows part we need to deploy the 7zip package too:
                folder_name = f"7zip-{sevenzip_vers['windows']}"
                src_folder = self.get_path(self.ctx.get_root_dir(), "tools", "windows", folder_name)
                dst_folder = self.get_path(proj_dir, "tools", "windows", folder_name)
                if not self.dir_exists(dst_folder):
                    logger.info("Adding windows 7zip package at %s", dst_folder)
                    self.copy_folder(src_folder, dst_folder)
    
                # Update the ignore elements:
                ignore_elems += ["",
                                 "# Ignore all the windows tools except the 7zip folder:",
                                 "tools/windows/*",
                                 "!tools/windows/7zip-*",
                                 "tools/linux/*"]
    
                # Should also install an requirements.txt file:
                dest_file = self.get_path(proj_dir, "tools", "requirements.txt")
                if not self.file_exists(dest_file):
                    logger.info("Installing pythong requirements file.")
                    content = ["# List here all the required python packages,"
                               "# Then call install_requirements.sh/install_requirements.bat"
                               "pylint",
                               "autopep8",
                               ""]
                    content = "\n".join(content)
                    self.write_text_file(content, dest_file)
  • Next step at this level is to also deploy some shell scripts to allow running the python app ⇒ I can use the NervProj cli.sh/cli.bat as a starting point, but I don't need to support building python from sources here.
  • OK, so now in the init command I'm also installing the required scripts as follow:
                # Should install the cli script files:
                dest_file = self.get_path(proj_dir, "cli.py")
                if not self.file_exists(dest_file):
                    logger.info("Writting cli python file %s", dest_file)
                    content = DEFAULT_CLI_PY_CONTENT
                    self.write_text_file(content, dest_file)
    
                dest_file = self.get_path(proj_dir, "cli.sh")
                if not self.file_exists(dest_file):
                    logger.info("Writting cli shell file %s", dest_file)
                    content = DEFAULT_CLI_SH_CONTENT
                    content = content.replace("${PROJ_NAME}", proj_name.lower())
                    # Use the linux python version below:
                    content = content.replace("${PY_VERSION}", py_vers['linux'])
                    self.write_text_file(content, dest_file, newline="\n")
    
                dest_file = self.get_path(proj_dir, "cli.bat")
                if not self.file_exists(dest_file):
                    logger.info("Writting cli batch file %s", dest_file)
                    content = DEFAULT_CLI_BAT_CONTENT
                    content = content.replace("${PROJ_NAME}", proj_name.upper())
                    # Use the windows versionq below:
                    content = content.replace("${PY_VERSION}", py_vers['windows'])
                    content = content.replace("${ZIP_VERSION}", sevenzip_vers['windows'])
                    self.write_text_file(content, dest_file)

⇒ And that is basically all I had to update: with that I can now create subproject with the NervProj framework that have their own python environment 👍!

  • blog/2022/0428_nervproj_standalone_py_env.txt
  • Last modified: 2022/04/27 22:01
  • by 127.0.0.1