Skip to content

Commit

Permalink
Changed hex.outdated to show if a dependency can be updated
Browse files Browse the repository at this point in the history
It now takes all dependent packages into account and simply prints a Yes
or a No for outdated packages.

Fixes hexpm#322
  • Loading branch information
lasseebert committed Dec 5, 2016
1 parent 02081ab commit 89777bb
Show file tree
Hide file tree
Showing 4 changed files with 67 additions and 18 deletions.
3 changes: 3 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,5 +1,8 @@
## v0.14.2-dev

### Bug fixes
* mix hex.outdated correctly tests if a package can be updated

## v0.14.1 (2016-11-24)

### Enhancements
Expand Down
32 changes: 22 additions & 10 deletions lib/mix/tasks/hex/outdated.ex
Original file line number Diff line number Diff line change
Expand Up @@ -117,13 +117,14 @@ defmodule Mix.Tasks.Hex.Outdated do
if Enum.empty?(values) do
Hex.Shell.info "No hex dependencies"
else
header = ["Dependency", "Current", "Latest", "Requirement"]
header = ["Dependency", "Current", "Latest", "Update possible"]
Utils.print_table(header, values)

message =
"A green version in latest means you have the latest " <>
"version of a given package. A green requirement means " <>
"your current requirement matches the latest version."
"version of a given package. Update possible indicates " <>
"if your current requirement matches the latest version.\n" <>
"Run `mix hex.outdated APP` to see requirements for a specific dependency."
Hex.Shell.info ["\n" | message]
end
end
Expand All @@ -137,8 +138,14 @@ defmodule Mix.Tasks.Hex.Outdated do
case Hex.Utils.lock(lock[dep.app]) do
[:hex, package, lock_version, _checksum, _managers, _deps] ->
latest_version = latest_version(package, lock_version, pre?)
req = dep.requirement
[[Atom.to_string(dep.app), lock_version, latest_version, req]]

requirements =
deps
|> get_requirements(dep.app)
|> Enum.map(fn [_, req_version] -> req_version end)
|> List.insert_at(0, dep.requirement)

[[Atom.to_string(dep.app), lock_version, latest_version, requirements]]
_ ->
[]
end
Expand Down Expand Up @@ -171,18 +178,23 @@ defmodule Mix.Tasks.Hex.Outdated do
List.last(versions)
end

defp format_all_row([package, lock, latest, req]) do
defp format_all_row([package, lock, latest, requirements]) do
outdated? = Hex.Version.compare(lock, latest) == :lt
latest_color = if outdated?, do: :red, else: :green

req_matches? = version_match?(latest, req)
req = req || ""
req_color = if req_matches?, do: :green, else: :red
req_matches? = Enum.all?(requirements, &(version_match?(latest, &1)))

{update_possible_color, update_possible} =
case {outdated?, req_matches?} do
{true, true} -> {:green, "Yes"}
{true, false} -> {:red, "No"}
{false, _} -> {:green, ""}
end

[[:bright, package],
lock,
[latest_color, latest],
[req_color, req]]
[update_possible_color, update_possible]]
end

defp version_match?(_version, nil), do: true
Expand Down
49 changes: 41 additions & 8 deletions test/mix/tasks/hex/outdated_test.exs
Original file line number Diff line number Diff line change
Expand Up @@ -45,6 +45,15 @@ defmodule Mix.Tasks.Hex.OutdatedTest do
end
end

defmodule OutdatedMultiDeps.Mixfile do
def project do
[app: :outdated_app,
version: "0.0.2",
deps: [{:baz, "0.1.0"},
{:bar, "0.1.0"}]]
end
end

test "outdated" do
Mix.Project.push OutdatedDeps.Mixfile

Expand All @@ -57,7 +66,7 @@ defmodule Mix.Tasks.Hex.OutdatedTest do

Mix.Task.run "hex.outdated"

bar = [:bright, "bar", :reset, " ", "0.1.0", :reset, " ", :green, "0.1.0", :reset, " ", :green, "0.1.0", :reset, " "]
bar = [:bright, "bar", :reset, " ", "0.1.0", :reset, " ", :green, "0.1.0", :reset, " ", :green, "", :reset, " "]
|> IO.ANSI.format
|> List.to_string

Expand All @@ -78,15 +87,15 @@ defmodule Mix.Tasks.Hex.OutdatedTest do

Mix.Task.run "hex.outdated", ["--all"]

bar = [:bright, "bar", :reset, " ", "0.1.0", :reset, " ", :green, "0.1.0", :reset, " ", :green, "0.1.0", :reset, " "]
bar = [:bright, "bar", :reset, " ", "0.1.0", :reset, " ", :green, "0.1.0", :reset, " ", :green, "", :reset, " "]
|> IO.ANSI.format
|> List.to_string

foo = [:bright, "foo", :reset, " ", "0.1.0", :reset, " ", :red, "0.1.1", :reset, " ", :green, "~> 0.1.0", :reset, " "]
foo = [:bright, "foo", :reset, " ", "0.1.0", :reset, " ", :red, "0.1.1", :reset, " ", :green, "Yes", :reset, " "]
|> IO.ANSI.format
|> List.to_string

ex_doc = [:bright, "ex_doc", :reset, " ", "0.0.1", :reset, " ", :red, "0.1.0", :reset, " ", :red, "~> 0.0.1", :reset, " "]
ex_doc = [:bright, "ex_doc", :reset, " ", "0.0.1", :reset, " ", :red, "0.1.0", :reset, " ", :red, "No", :reset, " "]
|> IO.ANSI.format
|> List.to_string

Expand All @@ -96,6 +105,30 @@ defmodule Mix.Tasks.Hex.OutdatedTest do
end
end

test "outdated --all with multiple dependent packages" do
Mix.Project.push OutdatedMultiDeps.Mixfile

in_tmp fn ->
Hex.State.put(:home, tmp_path())
Mix.Dep.Lock.write %{
foo: {:hex, :foo, "0.1.0"},
bar: {:hex, :bar, "0.1.0"},
baz: {:hex, :baz, "0.1.0"}
}

Mix.Task.run "deps.get"
flush()

Mix.Task.run "hex.outdated", ["--all"]

foo = [:bright, "foo", :reset, " ", "0.1.0", :reset, " ", :red, "0.1.1", :reset, " ", :red, "No", :reset, " "]
|> IO.ANSI.format
|> List.to_string

assert_received {:mix_shell, :info, [^foo]}
end
end

test "outdated --pre" do
Mix.Project.push OutdatedBetaDeps.Mixfile

Expand All @@ -108,15 +141,15 @@ defmodule Mix.Tasks.Hex.OutdatedTest do

Mix.Task.run "hex.outdated", []

beta = [:bright, "beta", :reset, " ", "1.0.0", :reset, " ", :green, "1.0.0", :reset, " ", :green, ">= 0.0.0", :reset, " "]
beta = [:bright, "beta", :reset, " ", "1.0.0", :reset, " ", :green, "1.0.0", :reset, " ", :green, "", :reset, " "]
|> IO.ANSI.format
|> List.to_string
assert_received {:mix_shell, :info, [^beta]}

Mix.Task.reenable "hex.outdated"
Mix.Task.run "hex.outdated", ["--pre"]

beta = [:bright, "beta", :reset, " ", "1.0.0", :reset, " ", :red, "1.1.0-beta", :reset, " ", :red, ">= 0.0.0", :reset, " "]
beta = [:bright, "beta", :reset, " ", "1.0.0", :reset, " ", :red, "1.1.0-beta", :reset, " ", :red, "No", :reset, " "]
|> IO.ANSI.format
|> List.to_string
assert_received {:mix_shell, :info, [^beta]}
Expand Down Expand Up @@ -227,11 +260,11 @@ defmodule Mix.Tasks.Hex.OutdatedTest do
Mix.Task.run "deps.get"
flush()

ex_doc = [:bright, "ex_doc", :reset, " ", "0.0.1", :reset, " ", :red, "0.1.0", :reset, " ", :red, "~> 0.0.1", :reset, " "]
ex_doc = [:bright, "ex_doc", :reset, " ", "0.0.1", :reset, " ", :red, "0.1.0", :reset, " ", :red, "No", :reset, " "]
|> IO.ANSI.format
|> List.to_string

bar = [:bright, "bar", :reset, " ", "0.1.0", :reset, " ", :green, "0.1.0", :reset, " ", :green, "0.1.0", :reset, " "]
bar = [:bright, "bar", :reset, " ", "0.1.0", :reset, " ", :green, "0.1.0", :reset, " ", :green, "", :reset, " "]
|> IO.ANSI.format
|> List.to_string

Expand Down
1 change: 1 addition & 0 deletions test/test_helper.exs
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,7 @@ unless :integration in ExUnit.configuration[:exclude] do
HexWeb.new_package("foo", "0.1.0", [], pkg_meta, auth)
HexWeb.new_package("foo", "0.1.1", [], pkg_meta, auth)
HexWeb.new_package("bar", "0.1.0", [foo: "~> 0.1.0"], pkg_meta, auth)
HexWeb.new_package("baz", "0.1.0", [foo: "0.1.0"], pkg_meta, auth)
HexWeb.new_package("beta", "1.0.0", [], pkg_meta, auth)
HexWeb.new_package("beta", "1.1.0-beta", [], pkg_meta, auth)
end

0 comments on commit 89777bb

Please sign in to comment.