Skip to content
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

NuGet fixes #734

Merged
merged 17 commits into from Apr 24, 2017
Merged

NuGet fixes #734

merged 17 commits into from Apr 24, 2017

Conversation

ghost
Copy link

@ghost ghost commented Apr 7, 2017

This pull request should fix everything mentioned #569, except for nuget.config customization. Premake now uses api.nuget.org to fetch required information about the packages.

I've tested this against the following NuGet packages:

C++:

  • boost
  • boost_filesystem-vc140
  • boost_system-vc140
  • sdl2.v140
  • sdl2.v140.redist
  • glew.v140
  • harfbuzz
  • physfs.v140
  • freetype2
  • assimp.v140
  • assimp.v140.redist
  • pugixml

C#:

  • Newtonsoft.Json
  • NUnit
  • SSH.NET

There is one problem where older C# packages (published before 2016 or sometime 2016?) might not work because the API response for them doesn't always contain a file listing. There isn't really anything that we can do about this, other than to inform the user and abort.

One thing to also note is that this will increase generation times for projects with NuGet packages. With 12 packages, I was getting generation times of around 20 seconds (api.nuget.org is slow).

We might want to consider caching the API requests to a file. If we had an asynchronous HTTP API, that could also help because then we could run requests in parallel. Any thoughts?

Anyway, I'd appreciate it if people with C# projects could try out this branch before it was merged, preferably with more and different packages (@tritao, @SoleilLapierre, @tvandijck?). I don't have any personal C# projects, so I only have a dummy project to test this with.

@tritao
Copy link
Contributor

tritao commented Apr 7, 2017

Sounds great, I'll test it out during the weekend.

Copy link
Contributor

@tvandijck tvandijck left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

So I have one thing that may make this a bit more complicated... but look here:
https://github.com/premake/premake-core/blob/master/premake5.lua#L67

Some teams use premake without curl, at which point the 'http' API is entirely compiled away..

https://github.com/premake/premake-core/blob/master/src/host/premake.c#L100

So I really think this nuget fix is awesome, but it will have to check in some places for this particular case, and basically just error out and say it cannot get the information from the nuget server...

for prj in p.workspace.eachproject(wks) do
for i = 1, #prj.nuget do
local package = prj.nuget[i]
local response, err, code = http.get(string.format("https://api.nuget.org/v3/registration1/%s/index.json", id:lower()))
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I really like this to be configurable, there is other nuget streams out there, and certainly within companies like ours (Blizzard) we host our own internal caching streams, through things like artifactory, and myget...

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I just tried this with MyGet, and while it looks like while they implement the same API as api.nuget.org, they don't return a file listing for the packages (at least if they were uploaded by their automatic packages.config tool). There's something weird going on here.

api.nuget.org doesn't return a file listing for all packages either, but from my testing that only seemed to happen with older packages.

If the API doesn't provide us with a file listing, the only other way that I can think of is to have Premake download and extract the packages.

Copy link
Author

@ghost ghost Apr 8, 2017

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like only "NuGet galleries" report the file listing to us and "NuGet.Server" does not. So, I'm going to see if I can make Premake download and extract the packages so that we can support both.

This would also resolve the issue where api.nuget.org doesn't always return the file listing for whatever reason (and the caching issue I mentioned in the OP).

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

API's and support aside, let's at least make this configurable... a nuget.serverlist = {}, or something...

Then as for the filelist.. for now, we can simple error... and if we hit it, we can look at implementing whatever is needed to get it to work... Internally here at Blizzard we are using NuGet.Server, so yeah, we're going to hit that, since those implementations only implement the V2 API of nuget, and it seems like you are querying the V3 API.. Which is all right, if we need it, we'll either get to it ourselves, or someone else who needs it will...

@@ -219,6 +220,13 @@
end


function m.NuGetHasHTTP(prj)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

that is a pretty smart solution ;) I like it...

@ghost
Copy link
Author

ghost commented Apr 10, 2017

How's this?

@ghost
Copy link
Author

ghost commented Apr 10, 2017

I did run into something else when testing this. Some packages, such as MySQL.Data depend on other packages, but this doesn't currently handle those dependencies. So that's going to need some fixing. Should we fix it before merging, or should we do it in a separate PR?

@tvandijck
Copy link
Contributor

I'd say, separate PR... I'm sure there will be many more nuget improvements over time...

@ghost
Copy link
Author

ghost commented Apr 10, 2017

Sure.

@SoleilLapierre
Copy link

I just tried from c5bf4b9 but I get errors when creating a NuGet dependency on NUnit. If I use:

nuget { "NUnit:3.6.0" }

then I get:

Running action 'vs2015'...
Examining NuGet package source 'https://api.nuget.org/v3/index.json'...
Error: ** Error: NuGet API error (0)
SSL connect error
schannel: failed to retrieve ALPN result

If leave out the :3.6.0 version number, the error becomes:

Running action 'vs2015'...
Generated Zaber.Plugins.sln...
Generated Zaber.Plugins/Zaber.Plugins.csproj...
Error: [string "src/actions/vstudio/vs2010_nuget.lua"]:9: attempt to perform arithmetic on a nil value

I was following the instructions in BUILD.txt to build Premake on Windows using VS2015. "premake5 test" fails with this build.

@ghost
Copy link
Author

ghost commented Apr 11, 2017

I think we're hitting a libcurl bug here (curl/curl#840), solution would be to update libcurl.

@ghost
Copy link
Author

ghost commented Apr 11, 2017

I've opened pull request #738 to update libcurl.


_x(2, '<Reference Include="%s">', path.getbasename(file))
_x(3, '<HintPath>%s</HintPath>', vstudio.path(prj, p.filename(prj.solution, string.format("packages\\%s.%s\\%s", id, packageAPIInfo.verbatimVersion or packageAPIInfo.version, file))))
_p(3, '<Private>True</Private>')
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

One thing to note about this which we've had to fix on our internal version - this doesn't respect NoCopyLocal. On our version we replaced this line with:
local cfg = project.getfirstconfig(prj)
if premake.config.isCopyLocal(prj, package, cfg) then
_p(3, 'True')
else
_p(3, 'False')
end

Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks for letting me know. I've fixed this in bde50fc.

aleksijuvani and others added 17 commits April 14, 2017 13:34
This was generated on a per-solution basis when one needed to be
generated for each project.
For C# projects, we need to get the assembly paths from the NuGet API,
instead of assuming that the package only contains one assembly with the
same name as the package.
Non-gallery sources (such as NuGet.Server) are currently unsupported due
to API limitations.
If a package has a lot of versions, the NuGet API returns multiple
"pages" of results, but we only looked at the first "page". This
happened with the "NLog" package for example.
@tvandijck tvandijck merged commit 473b2f1 into premake:master Apr 24, 2017
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

5 participants