Mengganti nama folder virtualenv tanpa merusaknya

162

Saya telah membuat folder dan menginisialisasi instance virtualenv di dalamnya.

$ mkdir myproject
$ cd myproject
$ virtualenv env

Ketika saya menjalankan (env)$ pip freeze, ini menunjukkan paket yang diinstal sebagaimana mestinya.

Sekarang saya ingin mengganti nama myproject/menjadi project/.

$ mv myproject/ project/

Namun, sekarang ketika saya berlari

$ . env/bin/activate
(env)$ pip freeze

katanya pip tidak diinstal. Bagaimana cara saya mengganti nama folder proyek tanpa merusak lingkungan?

Riley Watkins
sumber
1
Pertanyaan ini sudah lama dan sudah memiliki jawaban, tetapi saya harus bertanya-tanya, mengapa OP tidak bisa hanya memindahkan virtualenv ke tempat itu? Jelas itu tidak menyelesaikan keinginan untuk pindah / ganti nama, tetapi bukankah itu mengembalikan virtualenv yang berfungsi, atau apakah sudah putus asa putus?
Malik A. Rumi
2
Ya, Anda benar, itu akan memperbaiki env virtual, tetapi tidak menyelesaikan masalah.
Florian
November 2019, Python3. Solusi terbaik bagi saya adalah menggambarkan di aarongorka.com/blog/portable-virtualenv
Samir Sadek

Jawaban:

148

Anda perlu menyesuaikan instalasi Anda untuk menggunakan jalur relatif. virtualenvmenyediakan untuk ini dengan --relocatableopsi. Dari dokumen :

Biasanya lingkungan terikat pada jalur tertentu. Itu berarti Anda tidak dapat memindahkan lingkungan atau menyalinnya ke komputer lain. Anda dapat memperbaiki lingkungan agar dapat dipindahkan dengan perintah:

$ virtualenv - ENV yang terkait

CATATAN: ENV adalah nama lingkungan virtual dan Anda harus menjalankan ini dari luar direktori ENV.

Ini akan membuat beberapa file yang dibuat oleh setuptools atau mendistribusikan menggunakan jalur relatif, dan akan mengubah semua skrip untuk menggunakan activ_this.py alih-alih menggunakan lokasi interpreter Python untuk memilih lingkungan.

Catatan: Anda harus menjalankan ini setelah Anda menginstal paket apa pun ke lingkungan. Jika Anda membuat suatu lingkungan dapat dipindahkan, kemudian instal paket baru, Anda harus menjalankan virtualenv --relocatable lagi.

ire_and_curses
sumber
2
peringatan: Mengubah env ke relocatable tidak lebih dari membiarkan Anda memindahkan folder. (lihat Catatan: disalin dari dokumen) ... itu mungkin memiliki efek samping.
Ben Roberts
7
Opsi --relocatable saat ini memiliki sejumlah masalah, dan tidak dijamin berfungsi dalam semua keadaan. Ada kemungkinan bahwa opsi ini akan ditinggalkan dalam versi virtualenv masa depan. Juga, ini tidak membuat paket Anda lintas platform. Anda dapat memindahkan direktori, tetapi hanya dapat digunakan pada komputer lain yang sejenis.
The Demz
1
@TheDemz grep -EIr '\Wold_venv_name\W' /path/to/new_venvakan membantu menemukan shabang yang menggunakan venv lama, tetapi bukan verifikasi lengkap dari venv yang dipindahkan.
hobs
2
Selain itu, Anda harus mengedit .projectfile virtualenvwrapper , yang berisi lintasan ke kode sumber yang bergantung pada virtualenv, dengan asumsi Anda menggunakan virutalenvwrapper dan juga mengganti nama dir proyek agar sesuai dengan virtualenv baru.
hobs
Saya harus menonaktifkan virtualenv sebelum menjalankan ini.
antonagestam
108

Saya percaya "mengetahui mengapa" lebih penting daripada "mengetahui bagaimana" . Jadi, inilah pendekatan lain untuk memperbaikinya.

Ketika Anda menjalankan . env/bin/activate, itu benar-benar menjalankan perintah berikut (menggunakan /tmpmisalnya):

VIRTUAL_ENV="/tmp/myproject/env"
export VIRTUAL_ENV

Namun, Anda baru saja mengganti nama myprojectmenjadi project, sehingga perintah itu gagal dieksekusi. Itulah sebabnya ia mengatakan pip is not installed, karena Anda belum menginstal pipdi lingkungan sistem global dan virtualenv Anda piptidak bersumber dengan benar.

Jika Anda ingin memperbaikinya secara manual, ini caranya:

  1. Dengan editor favorit Anda seperti Vim, modifikasi /tmp/project/env/bin/activatebiasanya di baris 42:

    VIRTUAL_ENV='/tmp/myproject/env' => VIRTUAL_ENV='/tmp/project/env'

  2. Ubah /tmp/project/env/bin/pippada baris 1:

    #!/tmp/myproject/env/bin/python => #!/tmp/project/env/bin/python

Setelah itu, aktifkan envkembali lingkungan virtual Anda , dan Anda akan melihat bahwa Anda piptelah kembali lagi.

holys
sumber
6
Jika secara manual mengubah jalur diinginkan, maka harus dicatat bahwa ada lebih dari dua file yang dikode keras. Menemukan mereka semua dengan sesuatu seperti: grep -iHnR venv-name /path/to/venv-name | grep -v "^Binary file" | grep -i venv-name. Bahkan, saya perhatikan bahwa dalam salah satu contoh Django saya, banyak paket memiliki "path to Python sh-bang" di dalamnya.
Kevin
Ini sangat membantu saya. Saya pasti perlu tahu mengapa ... Terima kasih!
Jarvis
Berbeda dengan komentar Keven di atas, saya menemukan bahwa mengedit dua baris ini menyelesaikan semua masalah bagi saya sehubungan dengan pemindahan virtualenv. Mungkin ada beberapa use case yang tidak saya gunakan dan jadi tidak menemui masalah.
Menghapus
Gores itu! Hari ini saya mengalami masalah: ipython tidak akan berfungsi di dalam virtualenv. Untuk mengatasinya, saya mengedit header bash (apa namanya?) Dalam ipythonfile dan kemudian berfungsi dengan baik.
Menghapus
Hmm ini tidak berfungsi untuk saya, dan sepertinya skrip aktivasi saya tidak memiliki Baris 1 yang disebutkan di sini pada Langkah 2. Apakah ada yang berubah?
Evan Zamir
40

CATATAN: Sebagai @jb. menunjukkan, solusi ini hanya berlaku untuk mudah (kembali) dibuat virtualenv. Jika lingkungan membutuhkan beberapa jam untuk menginstal solusi ini tidak dianjurkan


Virtualvv sangat bagus karena mudah dibuat dan diubah; mereka membuat Anda tidak terkunci ke dalam satu konfigurasi. Jika Anda mengetahui persyaratan proyek, atau bisa mendapatkannya, Buat yang baruvirtualenv :

  • Buat requirements.txtfile

    (env)$ pip freeze > requirements.txt

    • Jika Anda tidak dapat membuat requirements.txtfile, periksa env/lib/pythonX.X/site-packagessebelum menghapus aslinya env.
  • Hapus yang ada (env)

    deactivate && rm -rf env

  • Buat yang baru virtualenv, aktifkan, dan instal persyaratan

    virtualenv env && . env/bin/activate && pip install -r requirements.txt


Atau, gunakan virtualenvwrapper untuk membuat segalanya lebih mudah karena semua virtualenv disimpan di lokasi terpusat

$(old-venv) pip freeze > temp-reqs.txt
$(old-venv) deactivate
$ mkvirtualenv new-venv
$(new-venv) pip install -r temp-reqs.txt
$(new-venv) rmvirtualenv old-venv
bnjmn
sumber
6
Nah bagi sebagian orang pip install -r requirements.txtbutuh beberapa jam (kompilasi C-ekstensi pihak ketiga pada raspberry pi).
jb.
4
Mungkin benar, tapi bagiku itu seperti kasus tepi. Saya masih berpikir ini mungkin solusi yang layak untuk banyak kasus.
bnjmn
Yah, banyak proyek (situs web Django, misalnya) hanya membutuhkan waktu 30 detik untuk menginstal semuanya, bahkan jika mereka memiliki beberapa lusin dependensi (asalkan Anda mengunduh semuanya terlebih dahulu dan menggunakan '--tidak ada indeks --find-links = downloadDir' )
Jonathan Hartley
1
@ bnjmn one-liner virtualenv env && pip install -r requirements.txtTIDAK akan menginstal persyaratan di lingkungan baru karena Anda tidak mengaktifkannya
Yarin
1
@Yarin, Terima kasih sudah menunjukkannya. Saya benar-benar merindukannya, menjadi virtualenv-wrapperpengguna sendiri (yang otomatis diaktifkan saat pembuatan). Saya telah memperbarui jawaban saya untuk memasukkan pengaktifan dengan virtualenvharapan menghindari kebingungan.
bnjmn
28

Saya selalu menginstal virtualenvwrapper untuk membantu. Dari prompt shell:

pip install virtualenvwrapper

Ada cara yang didokumentasikan dalam dokumen virtualenvwrapper - cpvirtualenv Inilah yang Anda lakukan. Pastikan Anda keluar dari lingkungan Anda dan kembali ke prompt shell. Ketik ini dengan nama yang diperlukan:

cpvirtualenv oldenv newenv

Dan kemudian, jika perlu:

rmvirtualenv oldenv

Untuk membuka newenv Anda:

workon newenv
Microwave
sumber
1
Jawaban microwave benar-benar harus menjadi metode yang diterima.
Jaxian
Ini hanya berfungsi jika seseorang menggunakan virtualenvwrapper, bukan hanya virtualenv. Jawaban dari @ryankdwyer ini lebih baik.
LS
Saya mengedit jawaban saya untuk mencerminkan bahwa seseorang harus menginstal 'virtualenvwrapper'. Dengan asumsi bahwa pengubahan nama lingkungan virtual sering terjadi, saya akan merekomendasikan cara ini.
Afrowave
Meskipun ini bergantung pada virtualenvwrapper, itu adalah yang paling sederhana. Dan itu bekerja dengan baik.
blasrodri
17

Anda dapat memperbaiki masalah Anda dengan mengikuti langkah-langkah ini:

  1. ganti nama direktori Anda
  2. jalankan kembali ini: $ virtualenv ..\path\renamed_directory
  3. virtualenv akan memperbaiki asosiasi direktori sambil meninggalkan paket Anda di tempat
  4. $ scripts/activate
  5. $ pip freeze untuk memverifikasi paket Anda sudah ada
  6. Peringatan penting, jika Anda memiliki dependensi jalur statis dalam file skrip di direktori virtualenv Anda, Anda harus mengubahnya secara manual.
ryankdwyer
sumber
1
Ini solusi yang sangat bagus untuk saya. Karena solusi ini dapat menghindari beberapa masalah yang terkait --relocatable, saya pikir solusi ini lebih baik daripada jawaban yang diterima. Sejauh ini, saya perhatikan bahwa banyak .pycfile di _new_name_/lib/python2.7masih merujuk _old_name_. Namun, itu tampaknya tidak mempengaruhi cara kerja lingkungan saya. Mungkin satu-satunya solusi yang lebih baik adalah menggunakan virtualenvwrapperatau beberapa utilitas lain yang disebutkan di antara jawaban di sini. Setidaknya solusi ini tidak perlu menginstal program tambahan.
LS
Bekerja seperti pesona!
AmirHossein
13

Namun cara lain untuk melakukannya yang bekerja untuk saya berkali-kali tanpa masalah adalah virtualenv-clone :

pip install virtualenv-clone
virtualenv-clone old-dir/env new-dir/env
Antony Hatchkins
sumber
Ini harus ditandai sebagai jawaban terbaik. Tangan ke bawah! Butuh beberapa waktu untuk mengkloning, jadi bersabarlah.
Amitrajit Bose
virtualenv-clone lalai untuk memperbarui prompt. Harus masuk melakukannya secara manual. Selain itu, sangat bagus.
user3667349
5

(di dalam folder proyek)

cd bin
sed -i 's/old_dir_name/new_dir_name/g' *

Jangan lupa nonaktifkan dan aktifkan

Ignacio
sumber
Bekerja dengan baik; Atau untuk jalur Linux:sed -i "s|$old_dir|$new_dir|g" bin/*
Destroyica
sed -i '.original' 's/old_dir_name/new_dir_name/g' *untuk mac
Alex
1

virtualenv --relocatable ENVbukan solusi yang diinginkan. Saya berasumsi kebanyakan orang menginginkan kemampuan untuk mengubah nama virtualenv tanpa efek samping jangka panjang.

Jadi saya telah membuat alat sederhana untuk melakukan hal itu. Halaman proyek untuk virtualenv-mv menguraikannya sedikit lebih detail, tetapi pada dasarnya Anda dapat menggunakan virtualenv-mvseperti Anda akan menggunakan implementasi sederhana mv(tanpa opsi).

Sebagai contoh:

virtualenv-mv myproject project

Harap dicatat bahwa saya baru saja meretas ini. Ini bisa pecah dalam keadaan yang tidak biasa (mis. Virtualenv yang dikaitkan) jadi harap berhati-hati (buat cadangan apa yang Anda tidak mampu kehilangan) dan beri tahu saya jika Anda mengalami masalah.

Enam
sumber