Question

J'ai essayé de comprendre cela, mais je vais avoir du mal à le faire. Je travaille actuellement sur un projet open source qui me demande de permettre à un utilisateur de appuyez sur dépôt distant sans déjà existant là-bas. Je veux éviter de vous connecter manuellement à un serveur et en cours d'exécution ou git init git init --bare.

Pour des raisons évidentes, je reçois l'erreur suivante lorsque vous essayez de pousser mon dépôt local vers un chemin qui ne pointe pas vers un référentiel existant sur le serveur distant:

fatal: '/var/repositories/myrepo' does not appear to be a git repository
fatal: The remote end hung up unexpectedly

Mais je voudrais être en mesure d'exécuter par exemple la commande suivante:

git push origin master

Et ont qui créent /myrepo dans /var/repositories si elle n'existe pas encore. Comment pourrais-je être en mesure d'y parvenir? Je suppose qu'il est une sorte de (global) git config paramètre serait probablement mis sur le serveur distant, ou autrement un git (spécifique référentiel) config localement, mais je ne pouvait pas comprendre.

Toute aide serait grandement appréciée!

Merci!

Était-ce utile?

La solution

  1. Payer et suivre la branche de la télécommande:

    git checkout -t origin/funbranch
    
  2. bifurquent de celui-ci:

    git checkout -b mybranch
    
  3. Poussez votre nouveau un, il va créer une nouvelle branche automatiquement sur la télécommande:

    git push origin mybranch
    

Il devrait dire "créé une nouvelle origine de la branche à distance / mybranch"

Si vous obtenez toujours « fin à distance Hung up », ça sonne comme une chose de sécurité. Avez-vous des clés SSH installées correctement, et avez-vous des droits d'écriture sur le serveur distant?

Le mode d'action des projets source la plus ouverte, vous devez créer une fourchette (un clone en soi) que vous utilisez pour faire votre travail parce que la plupart du temps, vous ne disposez pas des autorisations d'écriture sur le repo. Lorsque vous avez des changements, vous serez alors envoyer une demande de tirage au propriétaire du référentiel, et il / elle tirer de votre fourche les changements qu'ils veulent.

Autres conseils

Il n'y a actuellement aucun moyen d'utiliser git push pour créer un référentiel sur la télécommande. Le mieux que vous pouvez faire est d'écrire quelque chose d'un script en une ligne comme ceci:

#!/bin/bash
ssh $1 "git init --bare $2" &&
git push ssh://$1/$2

Si tout va bien vous pouvez ssh; si vous ne pouvez pas, vous pouvez utiliser une sorte d'accès de système de fichiers à créer simplement manuellement le repo par le dumping dans la structure fichier approprié / répertoire (peut-être créer localement et copier). Vous pouvez également créer une télécommande nommée le long du chemin.

Ce fut en fait l'un des plus fonctionnalités demandées sur l'enquête Git 2010 - alors peut-être que vous obtiendrez votre souhait de quelque temps l'année prochaine

Vous pouvez écrire un script d'emballage sur la télécommande, et commande préfix = "/ chemin / vers / wrapper" aux lignes des authorized_keys.

command="/usr/local/bin/gitaccess" ssh-rsa ...

Dans cette enveloppe vous vérifierait SSH_ORIGINAL_COMMAND. Git émet ces commandes:

git receive-pack '/path/provided' # when pushing
git upload-pack '/path/provided' # when pulling

Si SSH_ORIGINAL_COMMAND est pas vide et commence par l'un de ces derniers, vous vérifiez le chemin, créer le référentiel si nécessaire, installer une configuration dont vous avez besoin, et exécutez la commande.

Si SSH_ORIGINAL_COMMAND est vide et que vous voulez fournir aux utilisateurs un accès shell, vous invoquez un shell.

Si SSH_ORIGINAL_COMMAND n'est pas vide mais ne démarre pas avec une commande git, si vous voulez permettre aux utilisateurs d'avoir accès shell, vous exécutez simplement la commande fournie.

Voici un peu de code Ruby pour démontrer. Notez que je ne l'ai pas testé et il y a place à l'amélioration (par exemple nous ne devrions pas hardcode / bin / bash).

#!/usr/bin/env ruby
orig_command = ENV['SSH_ORIGINAL_COMMAND']
if orig_command.nil?
    # If you want to preserve shell access
    exec '/bin/bash' # not tested, I hope it's interactive if executed this way
end

cmd_parts = orig_command.match /([a-z-]+) '([a-z0-9.\/]+)'/
if cmd_parts.nil?
    # If you want to preserve shell access
    exec '/bin/bash', '-c', orig_command
end

command = cmd_parts[1]
path = '/var/repositories/'+cmd_parts[2] # not secured (could contain '..')

if command == 'git-receive-pack' || command == 'git-upload-pack'
    if not File.directory?(path)
        `git init --bare #{path}` # not secured, I didn't escape path
        # Do any configuration here
    end
    exec 'git-shell', '-c', "#{command} '#{path}'"
end

# If you want to preserve shell access
exec '/bin/bash', '-c', orig_command

Vous pouvez également passer un argument à ce script dans les authorized_keys pour identifier les utilisateurs et choisir si elles devraient avoir accès shell. Je fais aussi cela pour contrôler l'accès sur une base par dépôt. Si vous voulez porter cet argument aux crochets git, il suffit de créer une variable d'environnement.

Je sais que c'est une vieille question, mais je suis tombé sur ce tout googler autre chose.

La meilleure façon que je l'ai trouvé pour être en mesure de pousser à un serveur distant et avoir créer un référentiel si elle n'existe pas est d'utiliser gitolite. Regardez les guides d'installation pour cela, il est très facile à installer, et si vous changez certains paramètres de configuration, vous pouvez avoir utiliser votre / var / sortant des dépôts pour stocker les prises en pension.

Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top