J'ai une bibliothèque privée appelée some-library
(les noms réels ont été changés) avec un fichier d'installation ressemblant un peu à ceci:
setup(
name='some-library',
// Omitted some less important stuff here...
install_requires=[
'some-git-dependency',
'another-git-dependency',
],
dependency_links=[
'git+ssh://[email protected]/my-organization/some-git-dependency.git#Egg=some-git-dependency',
'git+ssh://[email protected]/my-organization/another-git-dependency.git#Egg=another-git-dependency',
],
)
Toutes ces dépendances Git peuvent être privées, de sorte que l'installation via HTTP n'est pas une option. Je peux utiliser python setup.py install
et python setup.py develop
dans le répertoire racine de some-library
sans problèmes.
Cependant, installer sur Git ne fonctionne pas:
pip install -vvv -e 'git+ssh://[email protected]/my-organization/[email protected]#Egg=some-library'
La commande échoue lorsqu'elle recherche some-git-dependency
, suppose à tort qu'elle doit obtenir la dépendance de PyPI, puis échoue après avoir conclu qu'elle ne dépend pas de PyPI. Ma première hypothèse était d'essayer de réexécuter la commande avec --process-dependency-links
, mais c'est ce qui s'est passé:
Cannot look at git URL git+ssh://[email protected]/my-organization/some-git-dependency.git#Egg=some-git-dependency
Could not find a version that satisfies the requirement some-git-dependency (from some-library) (from versions: )
Pourquoi produit-il cette vague erreur? Quelle est la bonne façon de pip install
un paquet avec des dépendances Git qui pourraient être privées?
Comment installer correctement un paquet avec des dépendances Git qui pourraient être privées?
Deux options
Utilisez dependency_links
comme vous le faites. Voir ci-dessous pour plus de détails.
En plus du dependency_links
dans votre setup.py, utilisez un dependency-links.txt
spécial qui collecte tous les packages requis. Ajoutez ensuite ce paquet dans exigences.txt. C'est mon option de recommandation, comme expliqué ci-dessous.
# dependency-links.txt
git+ssh://...@tag#Egg=package-name1
git+ssh://...@tag#Egg=package-name2
# requirements.txt (per deployed application)
-r dependency-links.txt
Bien que l’option 2 alourdisse la gestion des paquets, notamment en maintenant à jour le fichier dependency-links.txt, elle facilite grandement l’installation des paquets car vous pouvez oublier d’ajouter l’option --process-dependency-link
à pip install
.
Peut-être plus important encore, en utilisant dependency-links.txt, vous devez spécifier la version exacte à installer lors du déploiement, ce que vous voulez dans un environnement CI/CD - rien n’est plus risqué que d’installer some version . Du point de vue du mainteneur du paquet, il est courant et considéré comme une bonne pratique de spécifier une version minimale, telle que
# setup.py in a package
...
install_requires = [ 'foo>1.0', ... ]
C’est formidable, car cela permet à vos paquets de fonctionner correctement avec d’autres qui possèdent des dépendances similaires, voire éventuellement des versions différentes. Cependant, dans une application déployée, cela peut toujours causer des problèmes en cas de conflit entre les exigences. Par exemple. le paquet A est ok avec foo>1.0
, le paquet B veut foo<=1.5
et la version la plus récente est foo==2.0
. Avec dependency-links.txt, vous pouvez être spécifique et appliquer une version à tous les packages:
# dependency-links.txt
foo==1.5
La commande échoue quand elle cherche une dépendance à git,
Pour que cela fonctionne, vous devez ajouter --process-dependency-links pour que pip reconnaisse la dépendance à github, par exemple.
pip install --process-dependency-links -r private-requirements.txt
Notez que depuis pip 8.1.0 vous pouvez ajouter cette option à Requirements.txt. En revanche, il est appliqué à all packages installés et peut avoir des conséquences inattendues. Cela dit, je trouve que dependency-links.txt
est une solution plus sûre et plus facile à gérer.
Toutes ces dépendances Git peuvent être privées
Il y a trois options:
Ajoutez des collaborateurs sur chacun des référentiels des packages requis. Ces collaborateurs doivent avoir leurs clés ssh configurées avec github pour que cela fonctionne. Ensuite, utilisez git+ssh://...
Ajoutez une clé de déploiement à chacun des référentiels. L'inconvénient est que vous devez distribuer la clé privée correspondante à toutes les machines à déployer. Encore une fois, utilisez git+ssh://...
Ajoutez un jeton d'accès personnel au compte github contenant les référentiels privés. Ensuite, vous pouvez utiliser git+https://[email protected]/...
. L’inconvénient est que le jeton d’accès aura un accès en lecture + écriture sur tous les référentiels, publics et privés, sur le compte github correspondant. Du côté positif, la distribution et la gestion de clés privées par référentiel n’est plus nécessaire, et le cycle de la clé est beaucoup plus simple. Dans un environnement entièrement intégré où chaque développeur a accès à tous les référentiels, j'ai trouvé que c'était le moyen le plus efficace et le plus simple pour tout le monde. YMMV
Cela devrait également fonctionner pour les référentiels privés:
dependency_links = [
'git+ssh://[email protected]/my-organization/some-git-dependency.git@master#Egg=some-git-dependency',
'git+ssh://[email protected]/my-organization/another-git-dependency.git@master#Egg=another-git-dependency'
],
Si je fais référence à " pip install dependency links ", vous ne ferez pas référence au référentiel GitHub lui-même, mais à l'image tarball associée à ce référentiel GitHub:
dependency_links=[
'git+ssh://[email protected]/my-organization/some-git-dependency/tarball/master/#Egg=some-git-dependency',
'git+ssh://[email protected]/my-organization/another-git-dependency/tarball/master/#Egg=another-git-dependency',
],
avec "some-git-dependency
" étant le nom * et la version de la dépendance.
Vous devriez utiliser git + git quand url avec #Egg, comme ceci:
-e [email protected]:foo/my-repo.git#Egg=my-repo
Utilisez git + ssh dans la production sans #Egg, mais vous pouvez spécifier @version ou branch @master
git+ssh://[email protected]/foo/[email protected]
pour travailler avec les versions d'applications, utilisez git tagging Principes de base de Git - Marquage
"Ne peut pas regarder l'URL de git git + ssh: //[email protected]/my-organization/some-git-dependency.git#Egg=some-git-dependency" signifie que pip
ne peut pas aller chercher un html page à partir de cette URL pour rechercher des liens de téléchargement direct dans la page, c’est-à-dire que pip
ne reconnaît pas l’URL en tant que commande vcs, car il peut y avoir une différence entre le spécificateur d’exigence et la partie fragmentée dans l’URL de vcs.
Dans le cas d'une extraction VCS, vous devez également ajouter
#Egg=project-version
afin d'identifier le paquet pour lequel cette extraction doit être utilisée.Veillez à éviter les tirets dans le nom ou la version en les remplaçant par des traits de soulignement.
Check Dépendances non présentes dans PyPI
remplacez -
par un _
dans le package et la chaîne de version .
git+ssh://[email protected]/my-organization/some-git-dependency.git#Egg=some_git_dependency
et --allow-all-external
peut être utile.