-
Notifications
You must be signed in to change notification settings - Fork 69
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Support for providing username and password for curl downloads #195
Comments
Interesting idea. How do you think we'd handle a project that has two or more modules requiring authentication, but their credentials are different. I'm not familiar with the netrc format, so I don't know if there's an obvious convention for this. |
netrc format is this:
All lines are valid, where More info on curl's usage here: https://ec.haxx.se/usingcurl-netrc.html |
I think if the netrc file indicates that foo.com should have a username and password, then it's probably ok for any Would you be willing to put together a PR for this? I'd be happy to review it. I'm not sure how to test it though -- can Python's HTTPServer be set up locally to require this type of auth? Is there a standard environment variable we might want to use to override the |
I'll see what I can drum up! |
From my point of view, it's not about I really like the idea of |
Hi, I am in need of this feature in a near feature, so I might start working on it if you are willing to accept. |
Yes I'm happy to review. (Though please ping me if I miss an email and it seems like I'm not responding.) Here are the two main design issues as I understand them:
Let me know your thoughts. |
Yes, I declined the netrc approach when I started considering a CI idea, it would not be so feasible. This environment variable approach would be probably the safest option and the quickest. Just not to discard, I also did some investigation on some other options, and the git config url.insteaof sounds interesting. Because it could be used implicitly by the git plugin too. But for the curl plugin, it would require parsing the git config file and loading internally. There is a git config library for python, but I am not so sure it is needed for this use case. |
Hi, I've been thinking about this feature, and I've had two approaches:
What do you think? |
It's great to see traffic on this issue! I've long since moved on from the org that inspired my original submission but recently returned to using Peru and simultaneously working in Python for the first time in 15 years... but I have very little spare time nowadays. I'd say that designing this well could enable all of these credential resolution methods. I'd recommend choosing environment variables as the first implementation. Doing something as @oconnor663 suggests with a module name in the envvar should be a first pass expanding perhaps the domain of the target system, but these both are limited in applicability mostly to The VCS modules (git, hg, svn) should be configured the way their systems expect it. As such, I discourage putting credentials into
So, if Peru were to support envvars at a basic level enough to satisfy one scale level (maybe up to 10 modules requiring authentication; little effort put into deduplication: exercise left to implementor) and then choose the standard netrc format for the next scale level (beyond 10 modules) for the "curl" plugin, I think it would have a solid and secure interface for that plugin. The netrc implementation should read the file and pass the credentials into a HTTPPasswordMgr instance used by urllib. The other modules' credentials are set however their respective system specify and that's something left to the Peru user to configure safely using those systems (mostly VCS) credential storage. To properly support password auth for rsync, Peru would have to set |
Perfect, that's correct.
I totally agree. Maybe we could come up with an alias to not break compatibility.
I totally disagree. I think we should come up with a solution for all cases. No one wants to spend extra time doing this "deduplication". If it is someone new coming to the tool, this person wants a solid tool. We don't want to scare people from here, do we?
How we would write to this file? Where are you storing this file? |
I could see this rolling out in a major release. In a minor release (e.g. 1.5.0), introduce the
To clarify, by deduplication, I mean enabling two modules that share credentials to reference the same credential set. For example, for two modules with the names PERU_PLUGIN_HTTP_CRED_FOO_USERNAME="asdf"
PERU_PLUGIN_HTTP_CRED_FOO_PASSWORD="hunter2"
PERU_PLUGIN_HTTP_CRED_BAR_USERNAME="asdf"
PERU_PLUGIN_HTTP_CRED_BAR_PASSWORD="hunter2" This will quickly grow unwieldy, obviously, but enabling envvars in this way lends itself to this following configuration in nearly all CI configurations, I speculate: # vela/drone object style
environment:
MYSERVICE_USER: "asdf"
MYSERVER_PASS: "hunter2"
PERU_PLUGIN_HTTP_CRED_FOO_USERNAME: "${MYSERVICE_USER}"
PERU_PLUGIN_HTTP_CRED_FOO_PASSWORD: "${MYSERVER_PASS}"
PERU_PLUGIN_HTTP_CRED_BAR_USERNAME: "${MYSERVICE_USER}"
PERU_PLUGIN_HTTP_CRED_BAR_PASSWORD: "${MYSERVER_PASS}" Eventually, this is going to have to be defined somehow, even if it ends up being a step in CI to avoid the introduction of a ton of envvars: curl module mypackage:
url: https://myservice.example.com/packages/mypackage-1.2.4.tar.gz
# this module _could_ automatically look at .netrc if it exists...
auth: netrc
# Untar the archive after fetching.
unpack: tar
# After the unpack, use this subdirectory as the root of the module.
export: mypackage # using Vela- and Drone-like config because I know it well enough to not look at docs ;-)
steps:
- name: write .netrc
image: alpine:latest
commands:
- echo "machine myservice.example.com login ${MYSERVICE_USER} password ${MYSERVICE_USER}" > .netrc
- chmod 400 .netrc
- name: get modules using netrc
image: buildinspace/peru:latest
commands:
- peru sync
# or specified instead of discovered in ./.netrc, ~/netrc, /etc/netrc, etc. whatever Python's netrc resolver does is fine
- peru sync --netrc .netrc
- name: get modules using envvars
image: buildinspace/peru:latest
environment:
- PERU_PLUGIN_HTTP_CRED_MYPACKAGE_USERNAME: ${MYSERVICE_USER}
- PERU_PLUGIN_HTTP_CRED_MYPACKAGE_PASSWORD: ${MYSERVICE_PASS}
commands:
- peru sync
# or specified instead of discovered in ./.netrc, ~/netrc, /etc/netrc, etc. whatever Python's netrc resolver does is fine
- peru sync --netrc .netrc
secrets:
- type: native
name: myservice_user
target: MYSERVICE_USER
- type: native
name: myservice_pass
target: MYSERVICE_PASS
Peru would not create it. Such feels like it could inevitably necessitate Peru allowing the definition of credentials in its configuration. That repeats a common security footgun pattern out of convenience! Most likely, a user would create it at repo setup time, including CI preparation steps. Some CI systems, notably Travis, enable users to store entire files in secret storage and that file is written to a predictable location on the runner or in the working directory before all CI steps. Vela and Drone write declared secrets as a file to a At a previous job, I accessed a number of services behind authentication and carried a |
Great, So, the flow would be something like that: At the developer machine the .netrc is located at default location which is usually ~/.netrc. At the CI, usually there is not a ~/.netrc because is outside the runner scope. So the user would have to add the information in a local .netrc and then pass the file location to peru in the command like you wrote there.
Have I understood correctly? If you all agree I may start working on that. |
One small idea that could be the best of both worlds: We could have |
This would be more cumbersome to set in env. variables in developer machine. It would good for CI though. I am not sure yet, but I feel that .netrc it is a more solid solution after all, for either CI or local development. |
This seems like a next-iteration feature of this feature. Perhaps a convention of something like |
It seems that I lost in this one. Let's see how it goes then. I will try to work on something in the next few days. About the alias, I am opening another issue mentioning this discussion. |
I'd like to retrieve dependencies from a private URL that requires credentials. In my current setup, I'm using
curl --netrc
, which enables me to put a hostname, username, and password into~/.netrc
.Poking through the source of the curl module, I see
peru/peru/resources/plugins/curl/curl_plugin.py
Line 82 in 42ad4ad
netrc parsing is, fortunately, a standard library feature of Python, through the aptly-named
netrc
library.The implementation of this all seems pretty straightforward but the configuration within peru is unclear. It would probably make sense for peru to read this file and populate the opener by default but I could see how some users may feel that's a security risk. So, a compromise may be opt-in in the peru.yml, an
auth
block:The text was updated successfully, but these errors were encountered: