-
Notifications
You must be signed in to change notification settings - Fork 35
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
Publishing a package is hard. New command 'pip publish'? #60
Comments
Huge 👍 for this. Related, there's a pip-init command (analogous to (See this thread for details of why I came looking for this) |
One of the super unobvious things that I ran into wrt passwords and |
Oh, that is very non-obvious! The thing I was publishing when I was thinking about how hard all of this was actually a tiny wrapper around |
Since nobody's said it yet - always, always publish with |
That's great advice which I didn't know. For the lazy people, https://pypi.python.org/pypi/twine |
FTR Distutils in Python 2.7.7+ uploads using HTTPS. |
Not verified HTTPS, that requires 2.7.9+ (I think it'll use verified then, though I haven't made sure of it). |
Also 3.4.3+ for Verified TLS on 3.x. But that doesn't matter a whole lot, because of the design of distutils means that if you want to say, upload wheel files for 2.6, 3.2, or 3.3 then you have to upload with a version of Python that doesn't verify HTTPS. |
@dstufft thanks Donald for explaining, I hadn't appreciated why part of the solution was to create a new tool, as well as fix the bug. Cool. I think this is all the more reason for a friendly and reliable |
I'm 100% all for this. Python is such a beautiful language, and its use cases range from simple "proof of concept" scripts to proprietary codebases. Yet it seems to be fading in popularity when compared with the Node community. I believe npm is a primary reason Node is so popular. The numbing simplicity of creating and publishing a Node package to the internet drastically lowers the bar for innovation, allowing more people to express their ideas and contributions. We need something like this for Python. What can I do to help? |
I just realized that the only thing I've said so far on this issue is "use twine". What I should really say is: Yes. |
been a while - as someone coming to pip from the Node.js + npm world where |
+1 |
Also note that coming from the Node world, there is |
I have been discovering the "python packaging world" the hard way in the last two months. Frankly I am quite disappointed as a Python teacher in how releasing your code is confusing and not straight as with all the other Python situations. So a huge +1 for a |
I am looking forward to this improvement. |
I still think tightly coupling the preferred publishing tool with the preferred package consumption tool again would be a major mistake, as the entire point of much of our work in PyPA has been to break the previous tight coupling of publishing tools and compatible download tools established by While
|
I think there's a big difference between putting virtualenv into tutorials, and putting uploading into pip. With virtualenv, you're adding a new tool and set of cognitive complexity to the first workflow people read about. With It's really important that we've separated installing+uploading from building. It's not clear to me what the value is in separating installing from uploading. (Besides "we've always done it that way.") What's the value add in having an ecosystem of competing upload tools? Can't we have one obvious way to upload a wheel? Is there any reason |
That's definitely part of it. If someone has prepared a package using flit, I don't want to make them learn about twine to get it published. There's also a difference in approach, though. I think that integrating build+upload into one command reduces the risk of mistakes where you upload the wrong files - for instance, if you make a last-minute change to the code and forget to rebuild the distributions. Other people would rather separate the steps so they can test the built distributions before uploading those precise files.
I guess that the push for features like this and I admire how this helps make rust approachable, and I think we should keep 'tool overload' in mind when designing packaging tools and documentation for Python (*). But standardising and unifying a collection of different tools which people already use is a much bigger task than designing a unified tool on a blank canvas. I don't want to say it's impossible, and give up on a potentially valuable endeavour before it is begun, but I would expect it to take many years of wrangling with people who, if they aren't happy, can easily walk away and keep using existing tools. (* It is of course a bit hypocritical for me to talk about tool overload after adding a new tool which serves the same purpose as existing tools.) |
The fact that Personally, I do not think pip should try to cover the development workflow. Specifically, I'm against adding As well as (I've just seen @takluyver's comment - basically I agree with pretty much everything he said). |
Oh, pip definitely shouldn't try to cover the development workflow: that would require implementing the functionality of tox, pipenv, flake8, pytest, flit, setuptools, and probably a bunch more I'm forgetting :-). Development is a complex activity that of course will require a wide variety of tools. But none of this gives me any sense of why Again, how does the pip/twine separation benefit users? Are there so many different ways to upload something to pypi that users benefit from a variety of options? |
I have to say I don't understand this part:
While I share the opinion that legacy support for something like distutils should never have happened, I don't see the connection between the fact that that support is there, and the notion that it's somehow bad practice to have the publication tools bundled with the language suite. Those are two completely separate things, and I'd like to understand what makes you think it's bad practice to offer those tools as part of the standard library. I'd also caution against drawing parallels between So that means comparing So I'd like to understand comments around why it would be a bad thing to (in limited fashion from what I'm reading so far) effect this kind of empowerment for users of Python. The added disk space adds up to "basically irrelevant" except for embedded systems (where no sane person would use a standard install anyway), and it sounds like the maintainers of |
(Note: thinking out loud in this comment so folks can see where I'm coming from in relation to this. I'll post a second comment describing a version of The root of the design problem we face at the C/C++:
Rust:
Java:
JavaScript:
Python:
So, in writing that out, I think my main concern is actually a factoring problem, in that I'd like users to be able to easily decide for themselves whether they want to configure a system as:
Point 1 is handled at the standard library level with That means it's only points 2 & 3 that impact the design of a |
I realised there's a way of tackling
From an end-user perspective, that would all end up looking like an "on first use" configuration experience for the From a maintenance perspective, while the existence of As an added bonus, all the documentation about extras would gain a concrete example that it can point to: |
Is attack surface your main concern? Because python already ships with multiple ways to make arbitrary HTTP requests, and doesn't ship with any PyPI credentials. So I'm having trouble seeing how having twine available would increase attack surface in a meaningful way? What's your threat model? |
@njsmith Every other part of Not putting the credentials on the machine in the first place is obviously the primary defence against compromise, but if the code is useless without credentials, why have it there, instead of designing the tooling to add the dependencies at the same time as you add the credentials? Keeping the dependencies separate also means that if a CVE is raised against the way twine accesses the system keyring, or the way it interacts with a user's account on PyPI, then it's only a vulnerability on systems that have twine installed, not on all systems that have pip installed. (A future version of pip would presumably raise the minimum required version of twine to a version without the vulnerability, but that would be a matter of dependency management hygiene, rather than urgent CVE response) That said, laying out the considerations as I did above means I now think most of the cases where this kind of concern really matters will be ones where the feature to be removed from the deployment environment is the entire build and installation toolchain, and that's already possible by doing So while I think the "extra"-based approach would be architecturally clearer (i.e. pip primarily remains an installation tool, but has some core publication functionality that relies on some optional dependencies), I don't think having it baked into the default install would create any unsolvable problems - worst case is that it would just give some folks an increased incentive to figure out how to remove pip from their deployment artifacts entirely, and there might end up being some future CVEs that impact more Python installs than they otherwise would have. |
I like @ncoghlan's idea -- have a pip command that's providing (optional) upload functionality, implemented using twine's public API, with an extra in pip to install the dependencies for it. :) |
This comment has been minimized.
This comment has been minimized.
It's been over 5 years since this issue got filed, and almost 2 years since the discussion died down and nothing happened. However, the entire world would still benefit from being able to type Just pick an approach, implement it, and then iterate on refining or even wholesale changing that implementation as the command sees adoption. As long as |
|
Why should one constantly add complaints if there's an issue open already? I guess only few would agree that Python packaging tooling is a pleasant thing to use. Besides, there are complaints now, and you're complaining about those. So maybe you should make up your mind on this matter.
Oh come on, the tooling is really not great compared to what we're seeing e.g. with NPM. Nobody's saying that the |
How many people work on and support npm? Wikipedia says "The company behind the npm software is npm, Inc, based in Oakland, California. [...] GitHub announced in March 2020 it is acquiring npm, Inc". The pip development team consists in total of about 5 people, all of whom only work on pip in their spare time. Frankly, I'd hope npm would be better than pip, with that level of disparity in development resource... |
Most of the work in the Python packaging space appears to be - with the sole exception of the new dependency resolver - unfunded and is carried out by volunteers in their free time. npm was VC-funded as early as 2013 and is now maintained by GitHub. Edit: heh, we posted almost the exact same thing at the exact same time. |
Yes, I don't challenge that. This is a totally acceptable explanation for why Python packaging is in such a bad shape. But still one should acknowledge that Python packaging is not great by any standards. Why that is the case is a different question. I'm thankful for the work people have put into the existing ecosystem either way, but this doesn't mean one cannot dislike or criticize it. |
That's a very absolute statement. There are certainly some standards by which Python packaging is fine:
Progress is slow. But it's not non-existent. And there are reasons why it's slow. People complaining that the volunteer labour "doesn't get things done faster" is one of the reasons it's slow, because it discourages and burns out the people whose freely given efforts are being dismissed as insufficient. I speak from experience here, as I know I'd do far more on pip if I didn't have to review so many issues that left me feeling demotivated.
However, finding ways to express such a dissatisfaction without implying some level of failure on the part of the people who voluntarily give their time to the work, is very hard. And people typically don't make any effort to do that, but simply throw out criticisms, and then follow up with "yes, but I appreciate the work people have done, I just dislike the result". And furthermore, how is complaining and criticising without offering any help, productive? If you were to submit a PR implementing a Never mind. I don't want to spend my Sunday worrying about explaining this to people. I'll go and find something more enjoyable to do. (And if that means I don't work on pip today, that's a good example of the consequences of this sort of discussion). |
+1 The fact that this was the first notification/issue thread I've read on this Sunday, is directly the cause of why I'm not spending any more time today to work on pip. |
Nobody said that.
I can very much empathize, I've been in your shoes before, many times. Maybe to clarify once more: I greatly appreciate the work and effort that people have put into PyPA and pip. But I think it's not okay to simply deny there are still many issues to be resolved when there clearly are issues. Because my impression was that this is exactly what was happening in response to @ArjunDandagi's and @Pomax's comments (and is the only reason why I joined the discussion)
First off, I never said "it sucks".
You can spend your time however you want to. Nobody's forcing you to do anything. |
Just to add, as a maintainer of various open source projects (not pip), a PR like this is probably not as helpful as it initially sounds. If you're not familiar with the internals of a project, your first attempt at writing a significant new feature is likely to need a lot of work, and therefore take up a lot of reviewers' time. It can also cost a lot of mental & emotional energy to explain to a well-intentioned contributor that the changes they've spent hours or days on are not going to be merged, and at least for me, this really drains my enthusiasm to work on a project. So, before contributing
You are allowed to criticise. @pfmoore suggested that it was not productive for you to do so. It looks like you've contributed to dissuading two maintainers from spending time on pip today, so I'd have to agree with him. The issue is that criticising Python packaging has been done to death for years. Anyone involved in Python packaging knows there are still plenty of warts and areas for improvement. So another round of "why isn't this fixed yet?" without engaging with the details of the discussion is not actually driving anything forwards. I will endeavour to resist the urge to reply again for at least the rest of the day. |
As a maintainer of a project used by many (pytest), I definitely concur with this statement. |
It would really help if people made concrete notes about what is not good in Python tools, and what is great in other tools. |
That would be the comment that started this thread. In
This is essentially frictionless, through a single tool. Yes, a competitor was written to address NPM's slowness, called "yarn": but they quite wisely decided to make it work in exactly the same way, so if you're coming to Python from the Node ecosystem at least (or if you're a long time user of Python and you started working with Node), you are effectively spoiled with an excellent publishing flow and tooling for that. There were dicsussions around having |
One suggestion - not intended as deflection, but as a genuine way for community members to help explore the design and maybe tease out some of the inevitable difficulties in integrating existing tools in such a front end. Maybe someone could build a tool that acted as nothing but that front end - providing the sort of user interface and workflow that node users find so attractive (I've never used node myself, so I have no feel for how npm "feels" in practice), while simply calling existing tools such as pip, twine etc, to deliver the actual functionality. If we had such a frontend - even in the form of a working prototype - it would be a lot easier to iterate on the design, and then, once the structure of the UI has been sorted out to work in the context of Python, we could look at how (or maybe if) we would integrate the command structure into pip or whatever. |
I think it is important to recognise that these complaints pertain to setuptools. Working with Flit and Poetry, which provide their own CLI, is not unlike working with npm. The addition of a |
I think it's probably also worth noting that a (small?) elephant in the room is that if you're coming to Python from another language, or even if it's your first exposure, you get told by nearly everyone that "how you install things" is through Having someone write a "unified" CLI proof of concept tool sounds like a great idea, and I'd be more than happy to provide input around the "npm experience" (having published a fair number of packages there), although I would not consider myself familiar enough with the various tools (or with enough time to deep-dive) to write that PoC myself. |
We had basically these same arguments about adding a For example, the motivation behind the unix philosophy does-one-thing-well tools for building distributions and installing wheels is that many downstream distributors feel the need to bootstrap their whole builds from source, and it's a pain in the ass to bootstrap a swiss army knife monolith like I also think that it's easy to look at I'm not saying that those ecosystems and all-in-one tools are worse than what we have or even that there's no benefits to them, but in the past we had an all-in-one tool for this: I think a bunch of individual tools with one or more wrapper CLIs for various purposes makes a lot of those problems much more tractable in the long term, and might help the people clamoring for a "single endpoint". |
To be honest, no-one had that sort of familiarity with the tools/ecosystem when they started. Why not just write a gross hack and see how things develop from there? mypip.py import subprocess
import sys
if __name__ == "__main__":
if sys.argv[1] == "publish":
subprocess.run(["twine", "upload"] + sys.argv[2:]
else:
subprocess.run(["pip"] + sys.argv[1:]) In all seriousness, that's the bare bones of a utility that adds a "publish" command to pip's CLI. Clearly, there's a lot of work to make even a prototype out of this, but if you started with that and actually used it, and improved it as you hit annoyances/rough edges, you'd pretty soon end up with something worth sharing. Most of the tools I've ever written started out like this. (I'm not trying to insist that you do this - just pointing out that "I don't know enough" is actually far less of a hurdle than people fear). |
No worries - for me personally, it's not just "I don't know enough" - I've done deep dives before, and they're usually fun - but it's very much also "and I don't have any free time for the next decade" because of the number of commitments I already have. |
That link gives a 404. |
It sure does, but it's not exactly hard to just go to packaging.python.org and find the current page, which is https://packaging.python.org/en/latest/guides/distributing-packages-using-setuptools/ |
Consider using a workflow tool instead, like Hatch, to simplify development: https://hatch.pypa.io/latest/publish/ |
I updated the link. You can also use |
Even after you've written a
setup.py
, publishing a package to PyPI is hard. Certainly I found it confusing the first time.The sequence of steps is complex and made stressful by all the decisions left to the user:
setup.py register
?)setup.py register
or by writing a.pypirc
?)setup.py upload
or withtwine
?)It would be neat to have a single command
pip publish
analogous tonpm publish
that did all of this, correctly.It would build whichever distributions are deemed fashionable (source + wheel). It you weren't logged in it would automatically run the wizard
pip register
.The text was updated successfully, but these errors were encountered: