hgext/zeroconf/__init__.py
author Boris Feld <boris.feld@octobus.net>
Wed, 20 Sep 2017 19:38:06 +0200
changeset 34836 537de0b14030
parent 34238 a6c18628dff1
child 42549 fa2071753dc2
permissions -rw-r--r--
phase: use a binary phase part to push through bundle2 (BC) The part we are using for pull is now used for push too. As we no longer use pushkey, pushkey hooks are no longer triggered. This is an obvious backward incompatible change. We could artificially trigger the pushkey hook within the bundle2 part, but this seemed too hacky to me. An option would be to disable by default this new mechanism for a couple of versions to help people migrate to `txnclose-phase`. I took the liberal and optimistic path to just turn it on by default directly. .. bc:: Push no longer triggers a pushkey hook when updating phases. Use the new `txnclose-phase` and `txnclose-phase` hooks instead. (Applies when both server and client use version 4.4 or above).
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
     1
# zeroconf.py - zeroconf support for Mercurial
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
     2
#
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
     3
# Copyright 2005-2007 Matt Mackall <mpm@selenic.com>
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
     4
#
8225
46293a0c7e9f updated license to be explicit about GPL version 2
Martin Geisler <mg@lazybytes.net>
parents: 8191
diff changeset
     5
# This software may be used and distributed according to the terms of the
10263
25e572394f5c Update license to GPLv2+
Matt Mackall <mpm@selenic.com>
parents: 9489
diff changeset
     6
# GNU General Public License version 2 or any later version.
8894
868670dbc237 extensions: improve the consistency of synopses
Cédric Duval <cedricduval@free.fr>
parents: 8866
diff changeset
     7
'''discover and advertise repositories on the local network
7606
e86ca711544d zeroconf: add extension documentation
David Soria Parra <dsp@php.net>
parents: 7295
diff changeset
     8
11504
6bfb76cb8873 zeroconf: small fixes in docstring
Martin Geisler <mg@lazybytes.net>
parents: 11340
diff changeset
     9
Zeroconf-enabled repositories will be announced in a network without
8003
14f27921932a zeroconf: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
    10
the need to configure a server or a service. They can be discovered
14f27921932a zeroconf: word-wrap help texts at 70 characters
Martin Geisler <mg@daimi.au.dk>
parents: 7874
diff changeset
    11
without knowing their actual IP address.
7606
e86ca711544d zeroconf: add extension documentation
David Soria Parra <dsp@php.net>
parents: 7295
diff changeset
    12
11504
6bfb76cb8873 zeroconf: small fixes in docstring
Martin Geisler <mg@lazybytes.net>
parents: 11340
diff changeset
    13
To allow other people to discover your repository using run
6bfb76cb8873 zeroconf: small fixes in docstring
Martin Geisler <mg@lazybytes.net>
parents: 11340
diff changeset
    14
:hg:`serve` in your repository::
7606
e86ca711544d zeroconf: add extension documentation
David Soria Parra <dsp@php.net>
parents: 7295
diff changeset
    15
9218
d3db87d68337 zeroconf: use reST syntax for literal blocks
Martin Geisler <mg@lazybytes.net>
parents: 9078
diff changeset
    16
  $ cd test
d3db87d68337 zeroconf: use reST syntax for literal blocks
Martin Geisler <mg@lazybytes.net>
parents: 9078
diff changeset
    17
  $ hg serve
7606
e86ca711544d zeroconf: add extension documentation
David Soria Parra <dsp@php.net>
parents: 7295
diff changeset
    18
11504
6bfb76cb8873 zeroconf: small fixes in docstring
Martin Geisler <mg@lazybytes.net>
parents: 11340
diff changeset
    19
You can discover Zeroconf-enabled repositories by running
6bfb76cb8873 zeroconf: small fixes in docstring
Martin Geisler <mg@lazybytes.net>
parents: 11340
diff changeset
    20
:hg:`paths`::
7606
e86ca711544d zeroconf: add extension documentation
David Soria Parra <dsp@php.net>
parents: 7295
diff changeset
    21
9218
d3db87d68337 zeroconf: use reST syntax for literal blocks
Martin Geisler <mg@lazybytes.net>
parents: 9078
diff changeset
    22
  $ hg paths
d3db87d68337 zeroconf: use reST syntax for literal blocks
Martin Geisler <mg@lazybytes.net>
parents: 9078
diff changeset
    23
  zc-test = http://example.com:8000/test
7606
e86ca711544d zeroconf: add extension documentation
David Soria Parra <dsp@php.net>
parents: 7295
diff changeset
    24
'''
28296
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    25
from __future__ import absolute_import
7606
e86ca711544d zeroconf: add extension documentation
David Soria Parra <dsp@php.net>
parents: 7295
diff changeset
    26
28296
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    27
import os
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    28
import socket
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    29
import time
11340
938fefb57db5 hgext/zeroconf/__init__.py: Separate relative and absolute imports.
Renato Cunha <renatoc@gmail.com>
parents: 11005
diff changeset
    30
28296
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    31
from . import Zeroconf
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    32
from mercurial import (
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    33
    dispatch,
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    34
    encoding,
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    35
    extensions,
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    36
    hg,
28308
4de74eda1d65 zeroconf: import ui as uimod per test-check-module-imports
Augie Fackler <augie@google.com>
parents: 28296
diff changeset
    37
    ui as uimod,
28296
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    38
)
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    39
from mercurial.hgweb import (
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    40
    server as servermod
a73394e7b47c zeroconf: use absolute_import
timeless <timeless@mozdev.org>
parents: 28250
diff changeset
    41
)
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    42
29841
d5883fd055c6 extensions: change magic "shipped with hg" string
Augie Fackler <augie@google.com>
parents: 28308
diff changeset
    43
# Note for extension authors: ONLY specify testedwith = 'ships-with-hg-core' for
25186
80c5b2666a96 extensions: document that `testedwith = 'internal'` is special
Augie Fackler <augie@google.com>
parents: 18190
diff changeset
    44
# extensions which SHIP WITH MERCURIAL. Non-mainline extensions should
80c5b2666a96 extensions: document that `testedwith = 'internal'` is special
Augie Fackler <augie@google.com>
parents: 18190
diff changeset
    45
# be specifying the version(s) of Mercurial they are tested with, or
80c5b2666a96 extensions: document that `testedwith = 'internal'` is special
Augie Fackler <augie@google.com>
parents: 18190
diff changeset
    46
# leave the attribute unspecified.
29841
d5883fd055c6 extensions: change magic "shipped with hg" string
Augie Fackler <augie@google.com>
parents: 28308
diff changeset
    47
testedwith = 'ships-with-hg-core'
16743
38caf405d010 hgext: mark all first-party extensions as such
Augie Fackler <raf@durin42.com>
parents: 16688
diff changeset
    48
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    49
# publish
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    50
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    51
server = None
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    52
localip = None
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    53
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    54
def getip():
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    55
    # finds external-facing interface without sending any packets (Linux)
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    56
    try:
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    57
        s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    58
        s.connect(('1.0.0.1', 0))
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    59
        ip = s.getsockname()[0]
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    60
        return ip
16688
cfb6682961b8 cleanup: replace naked excepts with more specific ones
Brodie Rao <brodie@sf.io>
parents: 16683
diff changeset
    61
    except socket.error:
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    62
        pass
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    63
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    64
    # Generic method, sometimes gives useless results
8264
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
    65
    try:
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
    66
        dumbip = socket.gethostbyaddr(socket.gethostname())[2][0]
30885
564a96a56b73 zeroconf: fail nicely on IPv6 only system
Simon Farnsworth <simonfar@fb.com>
parents: 29841
diff changeset
    67
        if ':' in dumbip:
564a96a56b73 zeroconf: fail nicely on IPv6 only system
Simon Farnsworth <simonfar@fb.com>
parents: 29841
diff changeset
    68
            dumbip = '127.0.0.1'
564a96a56b73 zeroconf: fail nicely on IPv6 only system
Simon Farnsworth <simonfar@fb.com>
parents: 29841
diff changeset
    69
        if not dumbip.startswith('127.'):
8264
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
    70
            return dumbip
10317
192083a3e6fe zeroconf: gethostbyaddr may also fail with socket.herror
Augie Fackler <durin42@gmail.com>
parents: 10263
diff changeset
    71
    except (socket.gaierror, socket.herror):
8264
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
    72
        dumbip = '127.0.0.1'
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    73
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    74
    # works elsewhere, but actually sends a packet
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    75
    try:
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    76
        s = socket.socket(socket.AF_INET, socket.SOCK_DGRAM)
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    77
        s.connect(('1.0.0.1', 1))
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    78
        ip = s.getsockname()[0]
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    79
        return ip
16688
cfb6682961b8 cleanup: replace naked excepts with more specific ones
Brodie Rao <brodie@sf.io>
parents: 16683
diff changeset
    80
    except socket.error:
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    81
        pass
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    82
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    83
    return dumbip
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    84
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    85
def publish(name, desc, path, port):
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    86
    global server, localip
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    87
    if not server:
8264
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
    88
        ip = getip()
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
    89
        if ip.startswith('127.'):
7295
66d0fc108044 zeroconf: Don't break serve if no internet connection is present.
Augie Fackler <durin42@gmail.com>
parents: 7282
diff changeset
    90
            # if we have no internet connection, this can happen.
66d0fc108044 zeroconf: Don't break serve if no internet connection is present.
Augie Fackler <durin42@gmail.com>
parents: 7282
diff changeset
    91
            return
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    92
        localip = socket.inet_aton(ip)
8264
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
    93
        server = Zeroconf.Zeroconf(ip)
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    94
7845
c2cd8d772805 zeroconf: advertise repositories with hostname
Alexander Solovyov <piranha@piranha.org.ua>
parents: 7777
diff changeset
    95
    hostname = socket.gethostname().split('.')[0]
c2cd8d772805 zeroconf: advertise repositories with hostname
Alexander Solovyov <piranha@piranha.org.ua>
parents: 7777
diff changeset
    96
    host = hostname + ".local"
c2cd8d772805 zeroconf: advertise repositories with hostname
Alexander Solovyov <piranha@piranha.org.ua>
parents: 7777
diff changeset
    97
    name = "%s-%s" % (hostname, name)
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    98
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
    99
    # advertise to browsers
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   100
    svc = Zeroconf.ServiceInfo('_http._tcp.local.',
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   101
                               name + '._http._tcp.local.',
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   102
                               server = host,
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   103
                               port = port,
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   104
                               properties = {'description': desc,
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   105
                                             'path': "/" + path},
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   106
                               address = localip, weight = 0, priority = 0)
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   107
    server.registerService(svc)
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   108
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   109
    # advertise to Mercurial clients
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   110
    svc = Zeroconf.ServiceInfo('_hg._tcp.local.',
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   111
                               name + '._hg._tcp.local.',
7088
58b7b5ef6cd0 zeroconf: advertise a proper hostname for _hg services
Matt Mackall <mpm@selenic.com>
parents: 7087
diff changeset
   112
                               server = host,
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   113
                               port = port,
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   114
                               properties = {'description': desc,
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   115
                                             'path': "/" + path},
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   116
                               address = localip, weight = 0, priority = 0)
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   117
    server.registerService(svc)
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   118
18190
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   119
def zc_create_server(create_server, ui, app):
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   120
    httpd = create_server(ui, app)
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   121
    port = httpd.port
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   122
18190
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   123
    try:
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   124
        repos = app.repos
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   125
    except AttributeError:
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   126
        # single repo
27910
d2c5ad3deccb zeroconf: access repo on hgweb_mod properly (issue5036)
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25186
diff changeset
   127
        with app._obtainrepo() as repo:
d2c5ad3deccb zeroconf: access repo on hgweb_mod properly (issue5036)
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25186
diff changeset
   128
            name = app.reponame or os.path.basename(repo.root)
d2c5ad3deccb zeroconf: access repo on hgweb_mod properly (issue5036)
Gregory Szorc <gregory.szorc@gmail.com>
parents: 25186
diff changeset
   129
            path = repo.ui.config("web", "prefix", "").strip('/')
34238
a6c18628dff1 configitems: register the 'web.description' config
Boris Feld <boris.feld@octobus.net>
parents: 33178
diff changeset
   130
            desc = repo.ui.config("web", "description")
a6c18628dff1 configitems: register the 'web.description' config
Boris Feld <boris.feld@octobus.net>
parents: 33178
diff changeset
   131
            if not desc:
a6c18628dff1 configitems: register the 'web.description' config
Boris Feld <boris.feld@octobus.net>
parents: 33178
diff changeset
   132
                desc = name
18190
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   133
        publish(name, desc, path, port)
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   134
    else:
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   135
        # webdir
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   136
        prefix = app.ui.config("web", "prefix", "").strip('/') + '/'
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   137
        for repo, path in repos:
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   138
            u = app.ui.copy()
9488
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   139
            u.readconfig(os.path.join(path, '.hg', 'hgrc'))
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   140
            name = os.path.basename(repo)
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   141
            path = (prefix + repo).strip('/')
34238
a6c18628dff1 configitems: register the 'web.description' config
Boris Feld <boris.feld@octobus.net>
parents: 33178
diff changeset
   142
            desc = u.config('web', 'description')
a6c18628dff1 configitems: register the 'web.description' config
Boris Feld <boris.feld@octobus.net>
parents: 33178
diff changeset
   143
            if not desc:
a6c18628dff1 configitems: register the 'web.description' config
Boris Feld <boris.feld@octobus.net>
parents: 33178
diff changeset
   144
                desc = name
18190
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   145
            publish(name, desc, path, port)
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   146
    return httpd
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   147
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   148
# listen
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   149
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   150
class listener(object):
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   151
    def __init__(self):
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   152
        self.found = {}
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   153
    def removeService(self, server, type, name):
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   154
        if repr(name) in self.found:
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   155
            del self.found[repr(name)]
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   156
    def addService(self, server, type, name):
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   157
        self.found[repr(name)] = server.getServiceInfo(type, name)
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   158
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   159
def getzcpaths():
8264
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
   160
    ip = getip()
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
   161
    if ip.startswith('127.'):
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
   162
        return
63ea850b3312 zeroconf: guess ip for Zeroconf
Alexander Solovyov <piranha@piranha.org.ua>
parents: 8225
diff changeset
   163
    server = Zeroconf.Zeroconf(ip)
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   164
    l = listener()
7874
d812029cda85 cleanup: drop variables for unused return values
Peter Arrenbrecht <peter.arrenbrecht@gmail.com>
parents: 7845
diff changeset
   165
    Zeroconf.ServiceBrowser(server, "_hg._tcp.local.", l)
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   166
    time.sleep(1)
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   167
    server.close()
9488
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   168
    for value in l.found.values():
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   169
        name = value.name[:value.name.index('.')]
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   170
        url = "http://%s:%s%s" % (socket.inet_ntoa(value.address), value.port,
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   171
                                  value.properties.get("path", "/"))
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   172
        yield "zc-" + name, url
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   173
33178
a0068f49b5f6 zeroconf: blindly forward extra argument to the core config method
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 30885
diff changeset
   174
def config(orig, self, section, key, *args, **kwargs):
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   175
    if section == "paths" and key.startswith("zc-"):
9488
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   176
        for name, path in getzcpaths():
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   177
            if name == key:
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   178
                return path
33178
a0068f49b5f6 zeroconf: blindly forward extra argument to the core config method
Pierre-Yves David <pierre-yves.david@octobus.net>
parents: 30885
diff changeset
   179
    return orig(self, section, key, *args, **kwargs)
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   180
28038
72f2a19c5f88 zeroconf: forward all arguments passed to ui.configitems() wrapper
Yuya Nishihara <yuya@tcha.org>
parents: 27910
diff changeset
   181
def configitems(orig, self, section, *args, **kwargs):
72f2a19c5f88 zeroconf: forward all arguments passed to ui.configitems() wrapper
Yuya Nishihara <yuya@tcha.org>
parents: 27910
diff changeset
   182
    repos = orig(self, section, *args, **kwargs)
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   183
    if section == "paths":
9488
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   184
        repos += getzcpaths()
33a6213a974e zeroconf: code cleanup, fixing variable names to be meaningful
Alexander Solovyov <piranha@piranha.org.ua>
parents: 9443
diff changeset
   185
    return repos
7071
643c751e60b2 zeroconf: initial implementation
Matt Mackall <mpm@selenic.com>
parents:
diff changeset
   186
28250
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   187
def configsuboptions(orig, self, section, name, *args, **kwargs):
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   188
    opt, sub = orig(self, section, name, *args, **kwargs)
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   189
    if section == "paths" and name.startswith("zc-"):
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   190
        # We have to find the URL in the zeroconf paths.  We can't cons up any
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   191
        # suboptions, so we use any that we found in the original config.
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   192
        for zcname, zcurl in getzcpaths():
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   193
            if zcname == name:
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   194
                return zcurl, sub
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   195
    return opt, sub
6d0d11731e1c zeroconf: fix crash in "hg paths" when zeroconf server is up
Danek Duvall <danek.duvall@oracle.com>
parents: 28038
diff changeset
   196
10342
579aae5aa549 zeroconf: override default destination folder on clone
Henrik Stuart <hg@hstuart.dk>
parents: 10317
diff changeset
   197
def defaultdest(orig, source):
579aae5aa549 zeroconf: override default destination folder on clone
Henrik Stuart <hg@hstuart.dk>
parents: 10317
diff changeset
   198
    for name, path in getzcpaths():
579aae5aa549 zeroconf: override default destination folder on clone
Henrik Stuart <hg@hstuart.dk>
parents: 10317
diff changeset
   199
        if path == source:
579aae5aa549 zeroconf: override default destination folder on clone
Henrik Stuart <hg@hstuart.dk>
parents: 10317
diff changeset
   200
            return name.encode(encoding.encoding)
579aae5aa549 zeroconf: override default destination folder on clone
Henrik Stuart <hg@hstuart.dk>
parents: 10317
diff changeset
   201
    return orig(source)
579aae5aa549 zeroconf: override default destination folder on clone
Henrik Stuart <hg@hstuart.dk>
parents: 10317
diff changeset
   202
14104
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   203
def cleanupafterdispatch(orig, ui, options, cmd, cmdfunc):
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   204
    try:
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   205
        return orig(ui, options, cmd, cmdfunc)
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   206
    finally:
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   207
        # we need to call close() on the server to notify() the various
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   208
        # threading Conditions and allow the background threads to exit
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   209
        global server
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   210
        if server:
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   211
            server.close()
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   212
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   213
extensions.wrapfunction(dispatch, '_runcommand', cleanupafterdispatch)
23fc62e0a960 zeroconf: notify the Zeroconf threads when hg exits
Nicolas Dumazet <nicdumz.commits@gmail.com>
parents: 12076
diff changeset
   214
28308
4de74eda1d65 zeroconf: import ui as uimod per test-check-module-imports
Augie Fackler <augie@google.com>
parents: 28296
diff changeset
   215
extensions.wrapfunction(uimod.ui, 'config', config)
4de74eda1d65 zeroconf: import ui as uimod per test-check-module-imports
Augie Fackler <augie@google.com>
parents: 28296
diff changeset
   216
extensions.wrapfunction(uimod.ui, 'configitems', configitems)
4de74eda1d65 zeroconf: import ui as uimod per test-check-module-imports
Augie Fackler <augie@google.com>
parents: 28296
diff changeset
   217
extensions.wrapfunction(uimod.ui, 'configsuboptions', configsuboptions)
10342
579aae5aa549 zeroconf: override default destination folder on clone
Henrik Stuart <hg@hstuart.dk>
parents: 10317
diff changeset
   218
extensions.wrapfunction(hg, 'defaultdest', defaultdest)
18190
d57879e72e18 zeroconf: use port from server instead of picking port from config (issue3746)
Benoit Boissinot <benoit.boissinot@ens-lyon.org>
parents: 16743
diff changeset
   219
extensions.wrapfunction(servermod, 'create_server', zc_create_server)