Menggunakan instruksi RUN di Dockerfile dengan 'sumber' tidak berfungsi

274

Saya memiliki Dockerfile yang saya kumpulkan untuk menginstal lingkungan python vanilla (di mana saya akan menginstal aplikasi, tetapi di kemudian hari).

FROM ubuntu:12.04

# required to build certain python libraries
RUN apt-get install python-dev -y

# install pip - canonical installation instructions from pip-installer.org
# http://www.pip-installer.org/en/latest/installing.html
ADD https://bitbucket.org/pypa/setuptools/raw/bootstrap/ez_setup.py /tmp/ez_setup.py
ADD https://raw.github.com/pypa/pip/master/contrib/get-pip.py /tmp/get-pip.py
RUN python /tmp/ez_setup.py
RUN python /tmp/get-pip.py
RUN pip install --upgrade pip 

# install and configure virtualenv
RUN pip install virtualenv 
RUN pip install virtualenvwrapper
ENV WORKON_HOME ~/.virtualenvs
RUN mkdir -p $WORKON_HOME
RUN source /usr/local/bin/virtualenvwrapper.sh

Build berjalan ok sampai baris terakhir, tempat saya mendapatkan pengecualian berikut:

[previous steps 1-9 removed for clarity]
...
Successfully installed virtualenvwrapper virtualenv-clone stevedore
Cleaning up...
 ---> 1fc253a8f860
Step 10 : ENV WORKON_HOME ~/.virtualenvs
 ---> Running in 8b0145d2c80d
 ---> 0f91a5d96013
Step 11 : RUN mkdir -p $WORKON_HOME
 ---> Running in 9d2552712ddf
 ---> 3a87364c7b45
Step 12 : RUN source /usr/local/bin/virtualenvwrapper.sh
 ---> Running in c13a187261ec
/bin/sh: 1: source: not found

Jika saya lske direktori itu (hanya untuk menguji bahwa langkah-langkah sebelumnya dilakukan) saya dapat melihat bahwa file ada seperti yang diharapkan:

$ docker run 3a87 ls /usr/local/bin
easy_install
easy_install-2.7
pip
pip-2.7
virtualenv
virtualenv-2.7
virtualenv-clone
virtualenvwrapper.sh
virtualenvwrapper_lazy.sh

Jika saya mencoba menjalankan sourceperintah, saya mendapatkan kesalahan 'tidak ditemukan' yang sama seperti di atas. Jika saya MENJALANKAN sesi shell interaktif, sumber tidak bekerja:

$ docker run 3a87 bash
source
bash: line 1: source: filename argument required
source: usage: source filename [arguments]

Saya dapat menjalankan skrip dari sini, dan kemudian dengan senang hati mengakses workon, mkvirtualenvdll.

Saya telah melakukan beberapa penggalian, dan awalnya tampak seolah-olah masalahnya mungkin terletak pada perbedaan antara bash sebagai shell login Ubuntu , dan dash sebagai shell sistem Ubuntu , dash tidak mendukung sourceperintah.

Namun, jawaban untuk ini tampaknya menggunakan '.' bukan source, tapi ini hanya menyebabkan runtime Docker meledak dengan pengecualian panik pergi.

Apa cara terbaik untuk menjalankan skrip shell dari instruksi Dockerfile RUN untuk menyiasati ini (saya kehabisan gambar dasar default untuk Ubuntu 12.04 LTS).

Hugo Rodger-Brown
sumber
2
Jadi jangan 'sumber' itu, jalankan saja perintahnya. Atau secara khusus jalankan skrip shell dengan 'bash'.
Alister Bulman
Mencoba itu - walaupun skrip tidak gagal, saya tidak mendapatkan akses ke berbagai perintah, yang saya inginkan. Masalah ini adalah hal yang sama - github.com/dotcloud/docker/issues/2847
Hugo Rodger-Brown
2
Yang mana, memikirkannya, benar. Virtualenvwrapper mungkin tidak masuk akal dalam lingkungan wadah. Saya akan mendukungnya dan menggunakan virtualenv 'asli' sebagai gantinya.
Hugo Rodger-Brown
1
Cara yang lebih mendasar untuk mendekati ini adalah stackoverflow.com/questions/4732200/…
Gaurav Ojha
CobaCMD source activate django-py35
Belter

Jawaban:

316

RUN /bin/bash -c "source /usr/local/bin/virtualenvwrapper.sh"

chobo
sumber
67
Eh? Jika Anda sumber skrip di dalam shell yang hanya ada untuk perintah, itu tidak dapat memiliki efek yang langgeng pada setiap menjalankan perintah di masa depan, dengan asumsi bahwa jumlah total tindakannya adalah pengaturan variabel lingkungan. Jadi mengapa Anda menggunakan sourcesama sekali, vs adil bash /usr/local/bin/virtualenvwrapper.sh, dalam kasus itu?
Charles Duffy
13
RUN /bin/bash -c "source /usr/local/bin/virtualenvwrapper.sh; my_command; my_command; my_command;"
Leo
29
Ini tidak benar meskipun berfungsi. Baca docs.docker.com/engine/reference/builder/#run dan jangan berhenti setelah sampel kode kedua. Baca Catatan: yang segera berikut. Karena /bin/sh -cshell default, "shell form" dari RUN ini diterjemahkan menjadi RUN ["/bin/sh", "-c", "/bin/bash" "-c" "source /usr/local/bin/virtualenvwrapper.sh"]. Anda harus maju dan menggunakan "exec form" dari RUN sehingga Anda dapat mengambil shkeluar seperti ituRUN ["/bin/bash" "-c" "source /usr/local/bin/virtualenvwrapper.sh"]
Bruno Bronosky
8
Silakan lihat stackoverflow.com/a/45087082/117471 untuk memahami mengapa ini membuat bashbersarang di shdan karenanya harus dihindari.
Bruno Bronosky
4
Jawaban yang lebih baik ada di sini: stackoverflow.com/a/42216046/1663462
Chris Stryczynski
150

Jawaban Asli

FROM ubuntu:14.04
RUN rm /bin/sh && ln -s /bin/bash /bin/sh

Ini harus bekerja untuk setiap gambar dasar buruh pelabuhan Ubuntu. Saya biasanya menambahkan baris ini untuk setiap Dockerfile yang saya tulis.

Edit oleh pengamat yang bersangkutan

Jika Anda ingin mendapatkan efek "gunakan bashalih-alih shseluruh Dockerfile ini", tanpa mengubah dan mungkin merusak * OS di dalam wadah, Anda bisa memberi tahu Docker niat Anda . Itu dilakukan seperti itu:

SHELL ["/bin/bash", "-c"]

* Kerusakan yang mungkin terjadi adalah banyak skrip di Linux (pada instalasi Ubuntu yang baru grep -rHInE '/bin/sh' /mengembalikan lebih dari 2.700 hasil) mengharapkan shell POSIX sepenuhnya /bin/sh. Bash shell bukan hanya POSIX plus builtin tambahan. Ada builtin (dan banyak lagi) yang berperilaku sama sekali berbeda dari yang ada di POSIX. Saya SEPENUHNYA mendukung menghindari POSIX (dan kekeliruan bahwa skrip yang tidak Anda uji pada shell lain akan berfungsi karena Anda pikir Anda menghindari basmisme) dan hanya menggunakan bashism. Tetapi Anda melakukannya dengan shebang yang tepat dalam naskah Anda. Tidak dengan menarik keluar shell POSIX dari bawah seluruh OS. (Kecuali jika Anda punya waktu untuk memverifikasi semua 2.700 skrip plus yang datang dengan Linux plus semua yang ada dalam paket yang Anda instal.)

Lebih detail dalam jawaban di bawah ini. https://stackoverflow.com/a/45087082/117471

Anubhav Sinha
sumber
18
Ini dapat disederhanakan sedikit:ln -snf /bin/bash /bin/sh
apottere
2
@ user1442219 ini menggantikan penerjemah perintah standar dari shkebash
Bhargav Nanekalva
27
ln -s /bin/bash /bin/shini ide yang buruk. target ubuntu / bin / sh untuk lari karena suatu alasan. dash adalah shell sepenuhnya posix yang perintah besarnya lebih cepat dari bash. menautkan / bin / sh ke bash akan secara drastis mengurangi kinerja server Anda. mengutip: wiki.ubuntu.com/DashAsBinSh
xero
7
Ini adalah hack kotor, bukan solusi. Jika skrip Anda dijalankan oleh shshell, tetapi Anda menginginkannya bash, solusi yang tepat adalah dengan shmeminta proses dipanggil bashsatu kali, misalnya bash -c 'source /script.sh && …', atau Anda bahkan dapat melangkah lebih jauh untuk menghindari bashisme (seperti source) sepenuhnya, dan sebagai gantinya memilih untuk hanya menggunakan setara POSIX yang valid, mis . /script.sh. (Pikirkan ruang setelah .!) Terakhir, jika skrip Anda dapat dieksekusi (bukan hanya sumber), jangan pernah membuat skrip Anda berbohong dengan #!/bin/shshebang jika tidak benar-benar kompatibel dengan sh. Gunakan #!/bin/bashsebagai gantinya.
Mark G.
7
Dan sekarang bagaimana cara saya downvote jawaban asli dan upvote edit oleh 'yang bersangkutan'?
Slava
65

Shell default untuk RUNinstruksi adalah ["/bin/sh", "-c"].

RUN "source file"      # translates to: RUN /bin/sh -c "source file"

Menggunakan instruksi SHELL , Anda dapat mengubah shell default untuk RUNinstruksi selanjutnya di Dockerfile:

SHELL ["/bin/bash", "-c"] 

Sekarang, shell default telah berubah dan Anda tidak perlu mendefinisikannya secara eksplisit di setiap instruksi RUN

RUN "source file"    # now translates to: RUN /bin/bash -c "source file"

Catatan Tambahan : Anda juga bisa menambahkan --loginopsi yang akan memulai shell login. Ini berarti ~/.bachrcmisalnya akan dibaca dan Anda tidak perlu sumber itu secara eksplisit sebelum perintah Anda

Ahmad Abdelghany
sumber
1
Pointer hebat untuk menggunakan --login- baru saja memikirkannya sendiri
mattexx
1
Dengan menggunakan SHELL ["/bin/bash", "-c", "-l"] saya dapat menggunakan pembaruan lebih lanjut untuk file .bashrc, yang memungkinkan saya untuk menjalankan perintah asdf dengan mudah.
Rowinson Gallego
46

Saya memiliki masalah yang sama dan untuk mengeksekusi pip install di dalam virtualenv saya harus menggunakan perintah ini:

RUN pip install virtualenv virtualenvwrapper
RUN mkdir -p /opt/virtualenvs
ENV WORKON_HOME /opt/virtualenvs
RUN /bin/bash -c "source /usr/local/bin/virtualenvwrapper.sh \
    && mkvirtualenv myapp \
    && workon myapp \
    && pip install -r /mycode/myapp/requirements.txt"

Saya harap ini membantu.

Andrea Grandi
sumber
Jika Anda berasal dari jawaban ROS, ya itu berhasil. Sesuatu seperti:RUN /bin/bash -c "source /opt/ros/melodic/setup.bash && \ cd /home && \ git clone https://angelos.p:[email protected]/inno/grpc-comms.git && \ cd grpc-comms && \ mkdir build && \ cd build && \ cmake .. && make"
angelos.p
44

Cara paling sederhana adalah dengan menggunakan operator titik di tempat sumber, yang merupakan setara sh dari sourceperintah bash :

Dari pada:

RUN source /usr/local/bin/virtualenvwrapper.sh

Menggunakan:

RUN . /usr/local/bin/virtualenvwrapper.sh
campuran
sumber
"source adalah builtin shell bourne dan POSIX` special 'builtin "- ss64.com/bash/source.html linux.die.net/man/1/sh ... . / sourcejuga menerima parameter posisi setelah nama file
Wes Turner
5
Ini tidak berfungsi karena setiap perintah RUN bekerja secara independen. Perubahan dari sourceatau .hilang ketika perintah RUN selesai. Lihat: stackoverflow.com/a/40045930/19501
amit
26

Jika Anda menggunakan Docker 1.12 atau lebih baru, gunakan saja SHELL!

Jawaban singkat:

umum:

SHELL ["/bin/bash", "-c"] 

untuk python vituralenv:

SHELL ["/bin/bash", "-c", "source /usr/local/bin/virtualenvwrapper.sh"]

Jawaban panjang:

dari https://docs.docker.com/engine/reference/builder/#/shell

SHELL ["executable", "parameters"]

Instruksi SHELL memungkinkan shell default yang digunakan untuk menggantikan shell form dari perintah. Shell default di Linux adalah ["/ bin / sh", "-c"], dan pada Windows adalah ["cmd", "/ S", "/ C"]. Instruksi SHELL harus ditulis dalam bentuk JSON di Dockerfile.

Instruksi SHELL sangat berguna pada Windows di mana ada dua shell asli yang umum digunakan dan sangat berbeda: cmd dan powershell, serta shell alternatif yang tersedia termasuk sh.

Instruksi SHELL dapat muncul beberapa kali. Setiap instruksi SHELL mengesampingkan semua instruksi SHELL sebelumnya, dan memengaruhi semua instruksi selanjutnya. Sebagai contoh:

FROM microsoft/windowsservercore

# Executed as cmd /S /C echo default
RUN echo default

# Executed as cmd /S /C powershell -command Write-Host default
RUN powershell -command Write-Host default

# Executed as powershell -command Write-Host hello
SHELL ["powershell", "-command"]
RUN Write-Host hello

# Executed as cmd /S /C echo hello
SHELL ["cmd", "/S"", "/C"]
RUN echo hello

Instruksi berikut dapat dipengaruhi oleh instruksi SHELL ketika form shell dari mereka digunakan dalam Dockerfile: RUN, CMD dan ENTRYPOINT.

Contoh berikut adalah pola umum yang ditemukan pada Windows yang dapat dirampingkan dengan menggunakan instruksi SHELL:

...
RUN powershell -command Execute-MyCmdlet -param1 "c:\foo.txt"
...

Perintah yang dipanggil oleh buruh pelabuhan adalah:

cmd /S /C powershell -command Execute-MyCmdlet -param1 "c:\foo.txt"

Ini tidak efisien karena dua alasan. Pertama, ada pemroses perintah cmd.exe yang tidak perlu (alias shell) yang dipanggil. Kedua, setiap instruksi RUN dalam bentuk shell membutuhkan kekuatan tambahan - perintah prefixing perintah.

Untuk membuat ini lebih efisien, satu dari dua mekanisme dapat digunakan. Salah satunya adalah menggunakan bentuk JSON dari perintah RUN seperti:

...
RUN ["powershell", "-command", "Execute-MyCmdlet", "-param1 \"c:\\foo.txt\""]
...

Sementara bentuk JSON tidak ambigu dan tidak menggunakan cmd.exe yang tidak perlu, itu memang membutuhkan lebih banyak verbositas melalui pengutipan dan pelolosan ganda. Mekanisme alternatifnya adalah dengan menggunakan instruksi SHELL dan form shell, membuat sintaksis yang lebih alami untuk pengguna Windows, terutama bila dikombinasikan dengan arahan parser escape:

# escape=`

FROM microsoft/nanoserver
SHELL ["powershell","-command"]
RUN New-Item -ItemType Directory C:\Example
ADD Execute-MyCmdlet.ps1 c:\example\
RUN c:\example\Execute-MyCmdlet -sample 'hello world'

Yang menghasilkan:

PS E:\docker\build\shell> docker build -t shell .
Sending build context to Docker daemon 4.096 kB
Step 1/5 : FROM microsoft/nanoserver
 ---> 22738ff49c6d
Step 2/5 : SHELL powershell -command
 ---> Running in 6fcdb6855ae2
 ---> 6331462d4300
Removing intermediate container 6fcdb6855ae2
Step 3/5 : RUN New-Item -ItemType Directory C:\Example
 ---> Running in d0eef8386e97


    Directory: C:\


Mode                LastWriteTime         Length Name
----                -------------         ------ ----
d-----       10/28/2016  11:26 AM                Example


 ---> 3f2fbf1395d9
Removing intermediate container d0eef8386e97
Step 4/5 : ADD Execute-MyCmdlet.ps1 c:\example\
 ---> a955b2621c31
Removing intermediate container b825593d39fc
Step 5/5 : RUN c:\example\Execute-MyCmdlet 'hello world'
 ---> Running in be6d8e63fe75
hello world
 ---> 8e559e9bf424
Removing intermediate container be6d8e63fe75
Successfully built 8e559e9bf424
PS E:\docker\build\shell>

Instruksi SHELL juga dapat digunakan untuk memodifikasi cara shell beroperasi. Misalnya, menggunakan SHELL cmd / S / C / V: ON | OFF pada Windows, semantik ekspansi variabel lingkungan yang tertunda dapat dimodifikasi.

Instruksi SHELL juga dapat digunakan di Linux jika shell alternatif diperlukan seperti zsh, csh, tcsh dan lainnya.

Fitur SHELL ditambahkan di Docker 1.12.

Mithril
sumber
20

Membangun jawaban di halaman ini saya akan menambahkan bahwa Anda harus menyadari bahwa setiap pernyataan RUN berjalan secara independen dari yang lain /bin/sh -c dan karena itu tidak akan mendapatkan vars lingkungan yang biasanya bersumber di shell login.

Cara terbaik yang saya temukan sejauh ini adalah menambahkan skrip ke /etc/bash.bashrcdan kemudian memanggil setiap perintah sebagai bash login.

RUN echo "source /usr/local/bin/virtualenvwrapper.sh" >> /etc/bash.bashrc
RUN /bin/bash --login -c "your command"

Misalnya Anda dapat menginstal dan mengatur virtualenvwrapper, membuat virtual env, mengaktifkannya ketika Anda menggunakan bash login, dan kemudian menginstal modul python Anda ke dalam env ini:

RUN pip install virtualenv virtualenvwrapper
RUN mkdir -p /opt/virtualenvs
ENV WORKON_HOME /opt/virtualenvs
RUN echo "source /usr/local/bin/virtualenvwrapper.sh" >> /etc/bash.bashrc
RUN /bin/bash --login -c "mkvirtualenv myapp"
RUN echo "workon mpyapp" >> /etc/bash.bashrc
RUN /bin/bash --login -c "pip install ..."

Membaca manual tentang file startup bash membantu memahami apa yang bersumber saat.

TomDotTom
sumber
1
Keren, berdasarkan solusi Anda apa yang saya lakukan hanya untuk menggambarkan adalah: ADD env-file /etc/profile.d/installerenv.sh RUN /bin/bash --login -c 'env' RUN /bin/bash -c 'rm /etc/profile.d/installerenv.sh' Jika kasus penggunaan seseorang menambahkan lebih banyak variabel lingkungan suntikan ke perspektif bangunan buruh pelabuhan seperti milik saya apakah saya akan merekomendasikan untuk melihat docs.docker.com/compose/yml / # env-file juga.
daniel.kahlenberg
1
Masalahnya dengan ini, saya percaya, adalah bahwa Anda tidak akhirnya melakukan cache hasil dari setiap RUNperintah, yang berarti bahwa Anda tidak dapat menginstal seluruh banyak dependensi proyek dan kemudian menyalin kode sumber dan mengambil keuntungan dari manfaat dari Caching langkah menengah Docker. Ini akan menginstal ulang semua dependensi proyek setiap saat.
erewok
Gunakan /etc/bashrcuntuk Redhat, bukan /etc/bash.bashrcseperti yang disebutkan di atas (Untuk Ubuntu)
Jordan Gee
Saya menggunakan /root/.bashrc untuk centos.
schmudu
LARI echo "source /yourscript.bash" >> /etc/bash.bashrc lakukan triknya. jika Anda menggunakan ros di dalam docker dan ingin mengatur lingkungan, inilah yang harus Anda lakukan
user27221
17

Menurut https://docs.docker.com/engine/reference/builder/#run shell default [Linux] RUNadalah is /bin/sh -c. Anda tampaknya mengharapkan bashism, jadi Anda harus menggunakan "formulir exec" RUNuntuk menentukan shell Anda.

RUN ["/bin/bash", "-c", "source /usr/local/bin/virtualenvwrapper.sh"]

Jika tidak, menggunakan "shell form" dari RUN dan menentukan shell yang berbeda akan menghasilkan shell yang bersarang.

# don't do this...
RUN /bin/bash -c "source /usr/local/bin/virtualenvwrapper.sh"
# because it is the same as this...
RUN ["/bin/sh", "-c", "/bin/bash" "-c" "source /usr/local/bin/virtualenvwrapper.sh"]

Jika Anda memiliki lebih dari 1 perintah yang membutuhkan shell yang berbeda, Anda harus membaca https://docs.docker.com/engine/reference/builder/#shell dan ubah shell default Anda dengan menempatkan ini sebelum perintah RUN Anda:

SHELL ["/bin/bash", "-c"]

Akhirnya, jika Anda telah menempatkan sesuatu di pengguna root .bashrc file yang Anda butuhkan, Anda dapat menambahkan -lbendera ke SHELLatau RUNperintah untuk membuatnya menjadi shell login dan memastikan bahwa itu bersumber.

Catatan: Saya sengaja mengabaikan fakta bahwa tidak ada gunanya untuk sumber skrip sebagai satu-satunya perintah dalam RUN.

Bruno Bronosky
sumber
1
SHELL ["/bin/sh", "-c", "-l"]jadi sumber ~ / .bashrc dll jika Anda memiliki pengaturan lingkungan dari wadah dasar
MortenB
1
@MortenB, tetapi Anda menentukan (salah ketik) /bin/shyang tidak akan menyelesaikan masalah bash yang tidak digunakan. Juga, ketika melakukan docker builditu tidak mungkin ada sesuatu yang berguna di .bashrc pengguna root yang Anda butuhkan. Tetapi, jika Anda memasukkan sesuatu di sana sebelumnya di Dockerfile (seperti mungkin a JAVA_HOME, maka ya. Saya akan mencatatnya dalam jawaban saya.
Bruno Bronosky
Maaf untuk kesalahan ketik, saya menggunakan pyenv yang perlu source ~ / .bashrc untuk mengatur path untuk versi python yang benar di gambar dasar saya. ini membuat saya menggunakan basis linux apa pun yang ada dan dengan dua baris menambahkan versi apa pun pada python. Seperti python 3.7 pada ubuntu16.04 di mana basis python adalah 3.5.2
MortenB
11

Menurut dokumentasi Docker

Untuk menggunakan shell yang berbeda, selain '/ bin / sh', gunakan formulir exec lewat di shell yang diinginkan. Sebagai contoh,

RUN ["/bin/bash", "-c", "echo hello"]

Lihat https://docs.docker.com/engine/reference/builder/#run

Gianluca Casati
sumber
Ini adalah jawaban benar yang SEBENARNYA. Penulis jawaban yang dipilih stackoverflow.com/a/25086628/117471 tampaknya hanya membaca contoh pertama dalam dokumentasi yang Anda tautkan. Mereka sepertinya tidak membaca paragraf selanjutnya yang telah Anda kutip.
Bruno Bronosky
4

Jika Anda sudah SHELLtersedia, Anda harus pergi dengan jawaban ini - jangan gunakan yang diterima, yang memaksa Anda untuk menaruh sisa file docker dalam satu perintah per komentar ini .

Jika Anda menggunakan versi Docker lama dan tidak memiliki akses SHELL, ini akan berfungsi selama Anda tidak memerlukan apa pun dari .bashrc(yang merupakan kasus yang jarang terjadi di Dockerfiles):

ENTRYPOINT ["bash", "--rcfile", "/usr/local/bin/virtualenvwrapper.sh", "-ci"]

Perhatikan bahwa -idiperlukan untuk membuat bash membaca file rc sama sekali.

Mohan
sumber
3

Anda mungkin ingin lari bash -v untuk melihat apa yang bersumber.

Saya akan melakukan hal berikut alih-alih bermain dengan symlink:

RUN echo "source /usr/local/bin/virtualenvwrapper.sh" >> /etc/bash.bashrc

vimdude
sumber
3

Saya juga memiliki masalah dalam menjalankan source di Dockerfile

Ini berjalan dengan baik untuk membangun CentOS 6.6 kontainer Docker, tetapi memberikan masalah dalam wadah Debian

RUN cd ansible && source ./hacking/env-setup

Beginilah cara saya mengatasinya, mungkin bukan cara yang elegan tapi inilah yang berhasil bagi saya

RUN echo "source /ansible/hacking/env-setup" >> /tmp/setup
RUN /bin/bash -C "/tmp/setup"
RUN rm -f /tmp/setup
vikas027
sumber
2

Ini mungkin terjadi karena sourcebuilt-in untuk bash daripada biner di suatu tempat di sistem file. Apakah niat Anda untuk skrip yang Anda cari mengubah wadah setelahnya?

Paul Morie
sumber
1
Skrip memperbarui wadah - tetapi jujur ​​saya mencoba melakukan sesuatu yang tidak masuk akal, sehingga telah melewati masalah.
Hugo Rodger-Brown
1

Saya akhirnya memasukkan barang-barang saya .profiledan bermutasi SHELLseperti

SHELL ["/bin/bash", "-c", "-l"]

# Install ruby version specified in .ruby-version
RUN rvm install $(<.ruby-version)

# Install deps
RUN rvm use $(<.ruby-version) && gem install bundler && bundle install

CMD rvm use $(<.ruby-version) && ./myscript.rb
mattexx
sumber
3
"-c" harus menjadi argumen terakhir (sebelum perintah. untuk dieksekusi)
peterk
0

Jika Anda hanya mencoba menggunakan pip untuk menginstal sesuatu ke virtualenv, Anda dapat memodifikasi PATH env untuk mencari di folder bin virtualenv terlebih dahulu

ENV PATH="/path/to/venv/bin:${PATH}"

Kemudian setiap pip installperintah yang mengikuti di Dockerfile akan menemukan / path / ke / venv / bin / pip terlebih dahulu dan menggunakannya, yang akan menginstal ke dalam virtualenv itu dan bukan sistem python.

shadfc
sumber