Installieren von Python-Paketen aus dem lokalen Dateisystemordner in virtualenv mit pip

345

Ist es möglich, Pakete mit pip aus dem lokalen Dateisystem zu installieren?

Ich habe python setup.py sdistfür mein Paket ausgeführt, das die entsprechende tar.gz-Datei erstellt hat. Diese Datei wird auf meinem System unter gespeichert /srv/pkg/mypackage/mypackage-0.1.0.tar.gz.

Jetzt möchte ich in einer virtuellen Umgebung Pakete installieren, die entweder von pypi oder von einem bestimmten lokalen Speicherort stammen /srv/pkg.

Ist das möglich?

PS Ich weiß, dass ich angeben kann pip install /srv/pkg/mypackage/mypackage-0.1.0.tar.gz. Das wird funktionieren, aber ich spreche davon, den /srv/pkgOrt als einen anderen Ort zu verwenden, an dem Pip suchen kann, wenn ich tippe pip install mypackage.

Chadgh
quelle
Ich wollte ein PyPi-Paket ohne setup.py vom WHL-Rad installieren. Es wurde installiert, nachdem ich eine korrekte Version für meine Python-Version heruntergeladen und ausgeführt hatte pip install <Path-to-WHL-file>.
Wiktor Stribiżew

Antworten:

136

Ich bin mir ziemlich sicher, dass das, wonach Sie suchen, --find-linksOption heißt .

Möglicherweise müssen Sie jedoch einen Dummy index.htmlfür Ihren lokalen Paketindex generieren, der die Links zu allen Paketen auflistet. Dieses Tool hilft:

https://github.com/wolever/pip2pi

Mikko Ohtamaa
quelle
100
pip install mypackage --no-index --find-links file:///srv/pkg/mypackagesollte arbeiten.
JFS
1
Es hilft. Und wir können die Option -i von pip verwenden, um sie als lokalen PyPI zu behandeln.
Diabloneo
Der entsprechende Befehl easy_install lauteteasy_install --allow-hosts=None --find-links file:///srv/pkg/mypackage mypackage
Wilfred Hughes
Ich musste eine Quellverteilungsdatei erstellen und nicht nur auf das Projekt- oder Paketverzeichnis verweisen, bevor es funktionieren würde. Das hat mich gestolpert. docs.python.org/3.6/distutils/sourcedist.html
Josh
3
Beachten Sie, dass --find-linksdie Suche in PyPI weiterhin möglich ist, wenn das Paket nicht am angegebenen Speicherort gefunden wird oder wenn eine neuere Version verfügbar ist. Unter Windows finde ich die Kombination mit --only-binary=packagename(oder --only-binary=:all:) außerordentlich nützlich. Dies verhindert, dass pip versucht, Pakete mit nativen Abhängigkeiten herunterzuladen, die nur Quelldistributionen auf PyPI haben (und daher kompiliert werden müssen). Dies ist der häufigste Grund, warum ich versuchen muss, aus einem Verzeichnis zu installieren. Im Gegensatz dazu --no-indexkann ich immer noch andere Pakete von PyPI installieren .
jpmc26
463

Wie wäre es mit::

pip install --help
...
  -e, --editable <path/url>   Install a project in editable mode (i.e. setuptools
                              "develop mode") from a local project path or a VCS url.

z.B, pip install -e /srv/pkg

Dabei ist / srv / pkg das Verzeichnis der obersten Ebene, in dem sich 'setup.py' befindet.

drpoo
quelle
49
Dadurch wird das Paket im Entwicklungsmodus installiert, dh es wird nur ein Link zu den Quellen erstellt. Wenn die Quellen zufällig verschoben oder gelöscht werden, schlägt der Import des Pakets fehl.
Trasplazio Garzuglio
3
@MarcoDinacci Interessant --editableist, dass es in das Verzeichnis des lokalen Pakets zu schauen scheint und die Quelle als Git-Repo festlegt, falls es eines gibt - etwas flexibler als nur ein Ordner. Ich kann jedoch keine Dokumentation dafür finden.
NotSimon
3
Dies ist zwar für die Installation eines bestimmten Pakets korrekt, insbesondere eines Pakets in der aktuellen / intensiven Entwicklung auf einem lokalen Computer oder einer VCS-URL. Die Frage zum Durchsuchen eines übergeordneten Verzeichnisses nach allen lokalen Paketquellen im Gegensatz zu einer bestimmten Paketquelle wird nicht beantwortet . Die akzeptierte Antwort funktioniert, wenn Sie ein Verzeichnis oder eine URL mit mehreren Paketen haben, aus denen Sie die Pip-Installation durchführen möchten.
Gavin
@MarcoDinacci Nehmen wir jedoch an, ein Benutzer lädt den Code herunter. Sie setzen es dort ein, wo sie das Programm haben wollen, wenn sie so intelligent sind. Warum sollten sie es bewegen wollen?
Zelphir Kaltstahl
1
@ Simon gibt es eine Möglichkeit, Pip zu sagen, dass er nicht nach einem Git-Repo suchen soll? Wenn ich do pip install -eden Code von der Git-Fernbedienung auschecke, möchte ich den Code so installieren, wie er ist (mit Änderungen, die noch nicht in der Fernbedienung enthalten sind).
Pedru
39

Ich installiere pyfuzzy, bin aber nicht in PyPI; es gibt die Nachricht zurück : No matching distribution found for pyfuzzy.

Ich habe die akzeptierte Antwort versucht

pip install  --no-index --find-links=file:///Users/victor/Downloads/pyfuzzy-0.1.0 pyfuzzy

Aber es funktioniert auch nicht und gibt den folgenden Fehler zurück:

Indizes ignorieren: https://pypi.python.org/simple pyfuzzy sammeln Es konnte keine Version gefunden werden, die die Anforderung pyfuzzy erfüllt (aus Versionen :) Keine passende Verteilung für pyfuzzy gefunden

Endlich habe ich dort einen einfachen guten Weg gefunden: https://pip.pypa.io/en/latest/reference/pip_install.html

Install a particular source archive file.
$ pip install ./downloads/SomePackage-1.0.4.tar.gz
$ pip install http://my.package.repo/SomePackage-1.0.4.zip

Der folgende Befehl hat also für mich funktioniert:

pip install ../pyfuzzy-0.1.0.tar.gz.

Hoffe es kann dir helfen.

Victor Choy
quelle
4
Das hat bei mir funktioniert. Ich habe die anderen Ansätze ausprobiert und bin durch einen Could not find a version that satisfiesFehler gestolpert . Vielen Dank.
Rair
21

Dies ist die Lösung, die ich letztendlich verwendet habe:

import pip


def install(package):
    # Debugging
    # pip.main(["install", "--pre", "--upgrade", "--no-index",
    #         "--find-links=.", package, "--log-file", "log.txt", "-vv"])
    pip.main(["install", "--upgrade", "--no-index", "--find-links=.", package])


if __name__ == "__main__":
    install("mypackagename")
    raw_input("Press Enter to Exit...\n")

Ich pieced diese zusammen aus pip Beispiele installieren sowie von Rikard Antwort auf andere Frage zusammengesetzt . Mit dem Argument "--pre" können Sie Nicht-Produktionsversionen installieren. Das Argument "--no-index" vermeidet das Durchsuchen der PyPI-Indizes. Die "--find-links =." Argumentensuche im lokalen Ordner (dies kann relativ oder absolut sein). Ich habe die Argumente "--log-file", "log.txt" und "-vv" zum Debuggen verwendet. Mit dem Argument "--upgrade" können Sie neuere Versionen gegenüber älteren installieren.

Ich habe auch einen guten Weg gefunden, sie zu deinstallieren. Dies ist nützlich, wenn Sie mehrere verschiedene Python-Umgebungen haben. Es ist das gleiche Grundformat, nur "Deinstallieren" anstelle von "Installieren", mit einer Sicherheitsmaßnahme, um unbeabsichtigte Deinstallationen zu verhindern:

import pip


def uninstall(package):
    response = raw_input("Uninstall '%s'? [y/n]:\n" % package)
    if "y" in response.lower():
        # Debugging
        # pip.main(["uninstall", package, "-vv"])
        pip.main(["uninstall", package])
    pass


if __name__ == "__main__":
    uninstall("mypackagename")
    raw_input("Press Enter to Exit...\n")

Der lokale Ordner enthält die folgenden Dateien: install.py, uninstall.py, mypackagename-1.0.zip

Devan Williams
quelle
1
Vielen Dank. Die "--find-links =." und "--no-index", wobei der Schlüssel zum Zusammenkleben eines Python-Skripts in meinem Dienstprogramm-Paket, das zuerst das Paket der alten Version aus Site-Paketen entfernt und dann ein tar.gz'ed-Paket aus einem Unterverzeichnis installiert des Utility-Package-Ordners (wusste nichts über --find-links =.), erstellt dann das Rad und installiert es. Alles automatisiert per Lot und Klick. Wenn jemand es will, werde ich einen Link posten. Upvoted.
JackLeEmmerdeur
15

Eine Option --find-links erledigt den Job und es funktioniert aus requirements.txtDatei!

Sie können Paketarchive in einem Ordner ablegen und das neueste verwenden, ohne die Anforderungsdatei zu ändern. Beispiel requirements:

.
└───requirements.txt
└───requirements
    ├───foo_bar-0.1.5-py2.py3-none-any.whl
    ├───foo_bar-0.1.6-py2.py3-none-any.whl
    ├───wiz_bang-0.7-py2.py3-none-any.whl
    ├───wiz_bang-0.8-py2.py3-none-any.whl
    ├───base.txt
    ├───local.txt
    └───production.txt

Jetzt in requirements/base.txtput:

--find-links=requirements
foo_bar
wiz_bang>=0.8

Eine gute Möglichkeit, proprietäre Pakete zu aktualisieren. Legen Sie einfach ein neues Paket in den Ordner

Auf diese Weise können Sie Pakete von local folderAND pypimit demselben einzigen Aufruf installieren :pip install -r requirements/production.txt

PS. In meiner Cookiecutter-Djangopackage- Gabel erfahren Sie , wie Sie Anforderungen aufteilen und die ordnerbasierte Anforderungsorganisation verwenden.

Janusz Skonieczny
quelle
Danke, das ist noch besser als das, woran ich gedacht habe!
FoundNil
11

Auf der Seite mit den Installationspaketen können Sie einfach Folgendes ausführen:

pip install / srv / pkg / mypackage

Dabei ist / srv / pkg / mypackage das Verzeichnis, das setup.py enthält .


Zusätzlich 1 können Sie es aus der Archivdatei installieren:

pip install ./mypackage-1.0.4.tar.gz

1 Obwohl in der Frage erwähnt, ist es aufgrund seiner Beliebtheit auch enthalten.

dim8
quelle
2
Dies sollte die Standardantwort sein. Wenn Sie genau wissen, wo sich Ihr Paket auf dem lokalen Computer befindet, müssen Sie nicht mit --find-links herumjagen.
Robert
6

Angenommen, Sie haben virtualenv und eine requirements.txtDatei, dann können Sie in dieser Datei definieren, wo Sie die Pakete erhalten:

# Published pypi packages 
PyJWT==1.6.4
email_validator==1.0.3
# Remote GIT repo package, this will install as django-bootstrap-themes
git+https://github.com/marquicus/django-bootstrap-themes#egg=django-bootstrap-themes
# Local GIT repo package, this will install as django-knowledge
git+file:///soft/SANDBOX/python/django/forks/django-knowledge#egg=django-knowledge
Marquicus
quelle
5

Anforderungen in requirements.txtund egg_dirals Verzeichnis haben

Sie können Ihren lokalen Cache erstellen:

$ pip download -r requirements.txt -d eggs_dir

Dann ist die Verwendung dieses "Caches" einfach wie folgt:

$ pip install -r requirements.txt --find-links=eggs_dir

Sławomir Lenart
quelle
1

Um nur von lokal zu installieren, benötigen Sie 2 Optionen:

  • --find-links: wo nach Abhängigkeiten gesucht werden soll. Das file://von anderen erwähnte Präfix ist nicht erforderlich .
  • --no-index: Suchen Sie in Pypi-Indizes nicht nach fehlenden Abhängigkeiten (Abhängigkeiten nicht installiert und nicht im --find-linksPfad).

Sie können also von jedem Ordner aus Folgendes ausführen:

pip install --no-index --find-links /srv/pkg /path/to/mypackage-0.1.0.tar.gz

Wenn Ihr Mypackage ordnungsgemäß eingerichtet ist, werden alle Abhängigkeiten aufgelistet. Wenn Sie Pip Download verwendet haben, um die Kaskade der Abhängigkeiten (dh Abhängigkeiten der Abhängigkeiten usw.) herunterzuladen, funktioniert alles.

Wenn Sie den Pypi-Index verwenden möchten, wenn er verfügbar ist, andernfalls auf lokale Räder zurückgreifen möchten, können Sie ihn entfernen --no-indexund hinzufügen --retries 0. Sie werden sehen, dass pip für eine Weile pausiert, während versucht wird, pypi auf eine fehlende Abhängigkeit zu überprüfen (eine, die nicht installiert ist), und wenn festgestellt wird, dass sie diese nicht erreichen kann, wird auf local zurückgegriffen. Es scheint keine Möglichkeit zu geben, pip anzuweisen, "zuerst nach lokalen und dann nach dem Index zu suchen".

Oliver
quelle
-1

Ich habe versucht, etwas wirklich Einfaches zu erreichen und bin kläglich gescheitert, wahrscheinlich bin ich dumm.

Wenn Sie ein Skript haben, Dockerfiledas eine Python-Paket-Zip-Datei herunterlädt (z. B. von GitHub) und diese dann installieren möchten, können Sie sie mit dem file:///Präfix installieren, wie im folgenden Beispiel gezeigt :

$ wget https://example.com/mypackage.zip
$ echo "${MYPACKAGE_MD5}  mypackage.zip" | md5sum --check -
$ pip install file:///.mypackage.zip

HINWEIS : Ich weiß, dass Sie das Paket sofort mit installieren können, pip install https://example.com/mypackage.zipaber in meinem Fall wollte ich die Prüfsumme überprüfen (nie paranoid genug) und bin kläglich gescheitert, als ich versucht habe, die verschiedenen Optionen zu verwenden, die pip / das #md5Fragment bietet .

Es war überraschend frustrierend, etwas so Einfaches direkt damit zu machen pip. Ich wollte nur eine Prüfsumme übergeben und pipüberprüfen, ob die Zip-Datei übereinstimmt, bevor ich sie installiere.

Ich habe wahrscheinlich etwas sehr Dummes getan, aber am Ende habe ich aufgegeben und mich dafür entschieden. Ich hoffe, es hilft anderen, etwas Ähnliches zu tun.

Aldo 'xoen' Giambelluca
quelle