docs: def prepare_runtime(self, runtime_dir, data):
          """Prepare runtime directory."""
          # Copy over Python process runtime (resolwe.process).
          import resolwe.process as runtime_package
  
          src_dir = os.path.dirname(inspect.getsourcefile(runtime_package))
          dest_package_dir = os.path.join(runtime_dir, PYTHON_RUNTIME_DIRNAME, 'resolwe', 'process')
          shutil.copytree(src_dir, dest_package_dir)
          os.chmod(dest_package_dir, 0o755)
  
          # Write python source file.
          source = data.process.run.get('program', '')
          program_path = os.path.join(runtime_dir, PYTHON_PROGRAM_FILENAME)
          with open(program_path, 'w') as file:
              file.write(source)
          os.chmod(program_path, 0o755)
  
          # Write serialized inputs.
          inputs = copy.deepcopy(data.input)
          hydrate_input_references(inputs, data.process.input_schema)
          hydrate_input_uploads(inputs, data.process.input_schema)
          inputs_path = os.path.join(runtime_dir, PYTHON_INPUTS_FILENAME)
  
          # XXX: Skip serialization of LazyStorageJSON. We should support
          # LazyStorageJSON in Python processes on the new communication protocol
          def default(obj):
              """Get default value."""
              class_name = obj.__class__.__name__
              if class_name == 'LazyStorageJSON':
                  return ''
  
              raise TypeError(f'Object of type {class_name} is not JSON serializable')
  
          with open(inputs_path, 'w') as file:
              json.dump(inputs, file, default=default)
  
          # Generate volume maps required to expose needed files.
          volume_maps = {
              PYTHON_RUNTIME_DIRNAME: PYTHON_RUNTIME_VOLUME,
              PYTHON_PROGRAM_FILENAME: PYTHON_PROGRAM_VOLUME,
              PYTHON_INPUTS_FILENAME: PYTHON_INPUTS_VOLUME,
          }
  
          return volume_maps