Class: Language::Python::Virtualenv::Virtualenv

Inherits:
Object
  • Object
show all
Defined in:
Library/Homebrew/language/python.rb

Overview

Convenience wrapper for creating and installing packages into Python virtualenvs.

Instance Method Summary collapse

Constructor Details

#initialize(formula, venv_root, python) ⇒ Virtualenv

Initializes a Virtualenv instance. This does not create the virtualenv on disk; #create does that.

Parameters:

  • formula (Formula)

    the active Formula

  • venv_root (Pathname, String)

    the path to the root of the virtualenv

  • python (String)

    which interpreter to use, e.g. "python" or "python2"


233
234
235
236
237
# File 'Library/Homebrew/language/python.rb', line 233

def initialize(formula, venv_root, python)
  @formula = formula
  @venv_root = Pathname.new(venv_root)
  @python = python
end

Instance Method Details

#createvoid

This method returns an undefined value.

Obtains a copy of the virtualenv library and creates a new virtualenv on disk.


242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
# File 'Library/Homebrew/language/python.rb', line 242

def create
  return if (@venv_root/"bin/python").exist?

  @formula.resource("homebrew-virtualenv").stage do |stage|
    old_pythonpath = ENV.delete "PYTHONPATH"
    begin
      staging = Pathname.new(stage.staging.tmpdir)

      ENV.prepend_create_path "PYTHONPATH", staging/"target/vendor"/Language::Python.site_packages(@python)
      %w[appdirs distlib filelock six].each do |virtualenv_dependency|
        @formula.resource("homebrew-#{virtualenv_dependency}").stage do
          @formula.system @python, *Language::Python.setup_install_args(staging/"target/vendor")
        end
      end

      ENV.prepend_create_path "PYTHONPATH", staging/"target"/Language::Python.site_packages(@python)
      @formula.system @python, *Language::Python.setup_install_args(staging/"target")
      @formula.system @python, "-s", staging/"target/bin/virtualenv", "-p", @python, @venv_root
    ensure
      ENV["PYTHONPATH"] = old_pythonpath
    end
  end

  # Robustify symlinks to survive python patch upgrades
  @venv_root.find do |f|
    next unless f.symlink?
    next unless (rp = f.realpath.to_s).start_with? HOMEBREW_CELLAR

    version = rp.match %r{^#{HOMEBREW_CELLAR}/[email protected](.*?)/}
    version = "@#{version.captures.first}" unless version.nil?

    new_target = rp.sub %r{#{HOMEBREW_CELLAR}/python#{version}/[^/]+}, Formula["python#{version}"].opt_prefix
    f.unlink
    f.make_symlink new_target
  end

  Pathname.glob(@venv_root/"lib/python*/orig-prefix.txt").each do |prefix_file|
    prefix_path = prefix_file.read

    version = prefix_path.match %r{^#{HOMEBREW_CELLAR}/[email protected](.*?)/}
    version = "@#{version.captures.first}" unless version.nil?

    prefix_path.sub! %r{^#{HOMEBREW_CELLAR}/python#{version}/[^/]+}, Formula["python#{version}"].opt_prefix
    prefix_file.atomic_write prefix_path
  end
end

#pip_install(targets) ⇒ void

This method returns an undefined value.

Installs packages represented by targets into the virtualenv.

Parameters:

  • targets (String, Pathname, Resource, Array<String, Pathname, Resource>)

    (A) token(s) passed to pip representing the object to be installed. This can be a directory containing a setup.py, a Resource which will be staged and installed, or a package identifier to be fetched from PyPI. Multiline strings are allowed and treated as though they represent the contents of a requirements.txt.


299
300
301
302
303
304
305
306
307
308
309
310
311
# File 'Library/Homebrew/language/python.rb', line 299

def pip_install(targets)
  targets = Array(targets)
  targets.each do |t|
    if t.respond_to? :stage
      next if t.name.start_with? "homebrew-"

      t.stage { do_install Pathname.pwd }
    else
      t = t.lines.map(&:strip) if t.respond_to?(:lines) && t.include?("\n")
      do_install t
    end
  end
end

This method returns an undefined value.

Installs packages represented by targets into the virtualenv, but unlike #pip_install also links new scripts to Formula#bin.

Parameters:

  • targets (String, Pathname, Resource, Array<String, Pathname, Resource>)

    (A) token(s) passed to pip representing the object to be installed. This can be a directory containing a setup.py, a Resource which will be staged and installed, or a package identifier to be fetched from PyPI. Multiline strings are allowed and treated as though they represent the contents of a requirements.txt.


318
319
320
321
322
323
324
325
326
# File 'Library/Homebrew/language/python.rb', line 318

def pip_install_and_link(targets)
  bin_before = Dir[@venv_root/"bin/*"].to_set

  pip_install(targets)

  bin_after = Dir[@venv_root/"bin/*"].to_set
  bin_to_link = (bin_after - bin_before).to_a
  @formula.bin.install_symlink(bin_to_link)
end