Merge pull request #248 from kujyp/behind_nginx_proxy

support changing the prefix of the path of the url
This commit is contained in:
Matthew Planchard 2019-05-05 13:17:12 -05:00 committed by GitHub
commit eb128b768a
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
4 changed files with 46 additions and 11 deletions

@ -21,9 +21,9 @@ except ImportError:
from StringIO import StringIO as BytesIO
try: # PY3
from urllib.parse import urljoin
from urllib.parse import urljoin, urlparse
except ImportError: # PY2
from urlparse import urljoin
from urlparse import urljoin, urlparse
log = logging.getLogger(__name__)
@ -59,6 +59,13 @@ def log_request():
log.info(config.log_req_frmt, request.environ)
@app.hook('before_request')
def print_request():
parsed = urlparse(request.urlparts.scheme + "://" + request.urlparts.netloc)
request.custom_host = parsed.netloc
request.custom_fullpath = parsed.path.rstrip('/') + '/' + request.fullpath.lstrip('/')
@app.hook('after_request')
def log_response():
log.info(config.log_res_frmt, { # vars(response)) ## DOES NOT WORK!
@ -80,7 +87,7 @@ def favicon():
@app.route('/')
def root():
fp = request.fullpath
fp = request.custom_fullpath
try:
numpkgs = len(list(packages()))
@ -90,11 +97,11 @@ def root():
# Ensure template() does not consider `msg` as filename!
msg = config.welcome_msg + '\n'
return template(msg,
URL=request.url,
URL=request.url.rstrip("/") + '/',
VERSION=__version__,
NUMPKGS=numpkgs,
PACKAGES=urljoin(fp, "packages/"),
SIMPLE=urljoin(fp, "simple/")
PACKAGES=fp.rstrip("/") + "/packages/",
SIMPLE=fp.rstrip("/") + "/simple/"
)
_bottle_upload_filename_re = re.compile(r'^[a-z0-9_.!+-]+$', re.I)
@ -197,7 +204,7 @@ def update():
@app.route('/packages')
@auth("list")
def pep_503_redirects(prefix=None):
return redirect(request.fullpath + "/", 301)
return redirect(request.custom_fullpath + "/", 301)
@app.post('/RPC2')
@ -261,7 +268,7 @@ def simple(prefix=""):
return redirect("%s/%s/" % (config.fallback_url.rstrip("/"), prefix))
return HTTPError(404, 'Not Found (%s does not exist)\n\n' % normalized)
fp = request.fullpath
fp = request.custom_fullpath
links = [(os.path.basename(f.relfn),
urljoin(fp, "../../packages/%s" % f.fname_and_hash(config.hash_algo)))
for f in files]
@ -284,7 +291,7 @@ def simple(prefix=""):
@app.route('/packages/')
@auth("list")
def list_packages():
fp = request.fullpath
fp = request.custom_fullpath
files = sorted(core.find_packages(packages()),
key=lambda x: (os.path.dirname(x.relfn),
x.pkgname,

@ -285,7 +285,7 @@ def store(root, filename, save_method):
def get_bad_url_redirect_path(request, prefix):
"""Get the path for a bad root url."""
p = request.fullpath
p = request.custom_fullpath
if p.endswith("/"):
p = p[:-1]
p = p.rsplit('/', 1)[0]

@ -292,6 +292,18 @@ def test_nonroot_root(testpriv):
resp.mustcontain("easy_install -i http://nonroot/priv/simple/ PACKAGE")
def test_nonroot_root_with_x_forwarded_host(testapp):
resp = testapp.get("/", headers={"X-Forwarded-Host": "forward.ed/priv/"})
resp.mustcontain("easy_install -i http://forward.ed/priv/simple/ PACKAGE")
resp.mustcontain("""<a href="/priv/packages/">here</a>""")
def test_nonroot_root_with_x_forwarded_host_without_trailing_slash(testapp):
resp = testapp.get("/", headers={"X-Forwarded-Host": "forward.ed/priv"})
resp.mustcontain("easy_install -i http://forward.ed/priv/simple/ PACKAGE")
resp.mustcontain("""<a href="/priv/packages/">here</a>""")
def test_nonroot_simple_index(root, testpriv):
root.join("foobar-1.0.zip").write("")
resp = testpriv.get("/priv/simple/foobar/")
@ -300,6 +312,14 @@ def test_nonroot_simple_index(root, testpriv):
assert links[0]["href"].startswith("/priv/packages/foobar-1.0.zip#")
def test_nonroot_simple_index_with_x_forwarded_host(root, testapp):
root.join("foobar-1.0.zip").write("")
resp = testapp.get("/simple/foobar/", headers={"X-Forwarded-Host": "forwarded.ed/priv/"})
links = resp.html("a")
assert len(links) == 1
assert links[0]["href"].startswith("/priv/packages/foobar-1.0.zip#")
def test_nonroot_simple_packages(root, testpriv):
root.join("foobar-1.0.zip").write("123")
resp = testpriv.get("/priv/packages/")
@ -308,6 +328,14 @@ def test_nonroot_simple_packages(root, testpriv):
assert links[0]["href"].startswith("/priv/packages/foobar-1.0.zip#")
def test_nonroot_simple_packages_with_x_forwarded_host(root, testapp):
root.join("foobar-1.0.zip").write("123")
resp = testapp.get("/packages/", headers={"X-Forwarded-Host": "forwarded/priv/"})
links = resp.html("a")
assert len(links) == 1
assert links[0]["href"].startswith("/priv/packages/foobar-1.0.zip#")
def test_root_no_relative_paths(testpriv):
"""https://github.com/pypiserver/pypiserver/issues/25"""
resp = testpriv.get("/priv/")

@ -96,7 +96,7 @@ def test_hashfile(tmpdir, algo, digest):
def test_redirect_prefix_encodes_newlines():
"""Ensure raw newlines are url encoded in the generated redirect."""
request = Namespace(
fullpath='/\nSet-Cookie:malicious=1;'
custom_fullpath='/\nSet-Cookie:malicious=1;'
)
prefix = '\nSet-Cookie:malicious=1;'
newpath = core.get_bad_url_redirect_path(request, prefix)