1
1
defmodule Mix.Tasks.Local.Hex do
2
2
use Mix.Task
3
3
4
- @ hex_url "https://hex.pm/installs/hex.ez"
5
- @ hex_requirement ">= 0.5.0"
4
+ @ hex_s3 "https://s3.amazonaws.com/s3.hex.pm"
5
+ @ hex_list_url @ hex_s3 <> "/installs/list.csv"
6
+ @ hex_archive_url @ hex_s3 <> "/installs/[VERSION]/hex.ez"
7
+ @ hex_requirement ">= 0.5.0"
6
8
7
9
@ shortdoc "Install hex locally"
8
10
9
11
@ moduledoc """
10
- Install hex locally from #{ @ hex_url } .
12
+ Install Hex locally.
11
13
12
14
mix local.hex
13
15
@@ -18,7 +20,9 @@ defmodule Mix.Tasks.Local.Hex do
18
20
"""
19
21
@ spec run ( OptionParser . argv ) :: boolean
20
22
def run ( args ) do
21
- url = @ hex_url <> "?elixir=" <> System . version
23
+ version = get_matching_version ( )
24
+ url = String . replace ( @ hex_archive_url , "[VERSION]" , version )
25
+
22
26
Mix.Tasks.Archive.Install . run [ url , "--shell" | args ]
23
27
end
24
28
@@ -75,4 +79,25 @@ defmodule Mix.Tasks.Local.Hex do
75
79
:erlang . raise ( kind , reason , stacktrace )
76
80
end
77
81
end
82
+
83
+ defp get_matching_version do
84
+ Mix.Utils . read_path! ( @ hex_list_url )
85
+ |> parse_csv
86
+ |> all_eligibile_versions
87
+ |> List . last
88
+ end
89
+
90
+ defp parse_csv ( body ) do
91
+ :binary . split ( body , "\n " , [ :global , :trim ] )
92
+ |> Enum . flat_map ( fn line ->
93
+ [ _hex | elixirs ] = :binary . split ( line , "," , [ :global , :trim ] )
94
+ elixirs
95
+ end )
96
+ |> Enum . uniq
97
+ end
98
+
99
+ defp all_eligibile_versions ( versions ) do
100
+ { :ok , current_version } = Version . parse ( System . version )
101
+ Enum . filter ( versions , & Version . compare ( & 1 , current_version ) != :gt )
102
+ end
78
103
end
0 commit comments