| author | wenzelm | 
| Tue, 22 Oct 2024 12:45:38 +0200 | |
| changeset 81229 | e18600daa904 | 
| parent 80039 | 0732ee5c8ee1 | 
| child 82610 | 3133f9748ea8 | 
| permissions | -rw-r--r-- | 
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 1 | /* Title: Pure/Tools/go_setup.scala | 
| 79976 | 2 | Author: Makarius | 
| 3 | ||
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 4 | Dynamic setup of Go component. | 
| 79976 | 5 | */ | 
| 6 | ||
| 7 | package isabelle | |
| 8 | ||
| 9 | ||
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 10 | object Go_Setup {
 | 
| 79976 | 11 | /* platform information */ | 
| 12 | ||
| 80008 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 13 | sealed case class Platform_Info(platform: String, go_platform: String) | 
| 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 14 |   extends Platform.Info {
 | 
| 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 15 | def paths: List[String] = List(platform, "pkg/tool/" + go_platform) | 
| 79982 
013558fd6fed
more accurate platform directories: pkg/tool structure is hardwired in "go";
 wenzelm parents: 
79976diff
changeset | 16 | |
| 
013558fd6fed
more accurate platform directories: pkg/tool structure is hardwired in "go";
 wenzelm parents: 
79976diff
changeset | 17 |     def download(base_url: String, version: String): String = {
 | 
| 80008 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 18 | val ext = if (is_windows) ".zip" else ".tar.gz" | 
| 79982 
013558fd6fed
more accurate platform directories: pkg/tool structure is hardwired in "go";
 wenzelm parents: 
79976diff
changeset | 19 |       Url.append_path(base_url, "go" + version + "." + go_platform.replace("_", "-") + ext)
 | 
| 
013558fd6fed
more accurate platform directories: pkg/tool structure is hardwired in "go";
 wenzelm parents: 
79976diff
changeset | 20 | } | 
| 79976 | 21 | } | 
| 22 | ||
| 80008 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 23 | val all_platforms: List[Platform_Info] = | 
| 79976 | 24 | List( | 
| 80008 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 25 |       Platform_Info("arm64-darwin", "darwin_arm64"),
 | 
| 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 26 |       Platform_Info("arm64-linux", "linux_arm64"),
 | 
| 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 27 |       Platform_Info("x86_64-darwin", "darwin_amd64"),
 | 
| 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 28 |       Platform_Info("x86_64-linux", "linux_amd64"),
 | 
| 
914c4a81027d
clarified signature: explicit type Platform.Info with derived operations;
 wenzelm parents: 
79982diff
changeset | 29 |       Platform_Info("x86_64-windows", "windows_amd64"))
 | 
| 79976 | 30 | |
| 80038 | 31 | def check_platform(spec: String): String = Platform.Info.check(all_platforms, spec) | 
| 79976 | 32 | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 33 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 34 | /* Go download and setup */ | 
| 79976 | 35 | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 36 | def default_platform: String = | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 37 | Isabelle_Platform.self.ISABELLE_PLATFORM(windows = true, apple = true) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 38 | def default_target_dir: Path = Components.default_components_base | 
| 79976 | 39 | val default_url = "https://go.dev/dl" | 
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 40 |   def default_version: String = Isabelle_System.getenv_strict("ISABELLE_GO_VERSION")
 | 
| 79976 | 41 | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 42 | def go_setup( | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 43 | platforms: List[String] = List(default_platform), | 
| 79976 | 44 | base_url: String = default_url, | 
| 45 | version: String = default_version, | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 46 | target_dir: Path = default_target_dir, | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 47 | progress: Progress = new Progress, | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 48 | force: Boolean = false | 
| 79976 | 49 |   ): Unit = {
 | 
| 80038 | 50 | platforms.foreach(check_platform) | 
| 79976 | 51 | |
| 52 | ||
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 53 | /* component directory */ | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 54 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 55 | val component_dir = | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 56 |       Components.Directory(target_dir + Path.basic("go-" + version)).create(permissive = true)
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 57 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 58 |     progress.echo("Component directory " + component_dir)
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 59 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 60 |     component_dir.write_settings("""
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 61 | ISABELLE_GOROOT="$COMPONENT" | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 62 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 63 | if [ -n "$ISABELLE_WINDOWS_PLATFORM64" -a -d "$ISABELLE_GOROOT/$ISABELLE_WINDOWS_PLATFORM64" ]; then | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 64 | ISABELLE_GOEXE="$ISABELLE_GOROOT/$ISABELLE_WINDOWS_PLATFORM64" | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 65 | elif [ -n "$ISABELLE_APPLE_PLATFORM64" -a -d "$ISABELLE_GOROOT/$ISABELLE_APPLE_PLATFORM64" ]; then | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 66 | ISABELLE_GOEXE="$ISABELLE_GOROOT/$ISABELLE_APPLE_PLATFORM64" | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 67 | elif [ -d "$ISABELLE_GOROOT/$ISABELLE_PLATFORM64" ]; then | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 68 | ISABELLE_GOEXE="$ISABELLE_GOROOT/$ISABELLE_PLATFORM64" | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 69 | fi | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 70 | """) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 71 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 72 | File.write(component_dir.platform_props, | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 73 | (for ((a, b) <- all_platforms.groupBy(_.family_name).iterator) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 74 |         yield a + " = " + b.flatMap(_.paths).mkString(" ")
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 75 |       ).mkString("", "\n", "\n"))
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 76 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 77 |     for (old <- proper_string(Isabelle_System.getenv("ISABELLE_GOROOT"))) {
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 78 | Components.update_components(false, Path.explode(old)) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 79 | } | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 80 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 81 | Components.update_components(true, component_dir.path) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 82 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 83 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 84 | /* download and setup */ | 
| 79976 | 85 | |
| 86 |     Isabelle_System.with_tmp_dir("download") { download_dir =>
 | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 87 |       for (platform <- all_platforms if platforms.exists(platform.is)) {
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 88 | val platform_dir = component_dir.path + platform.path | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 89 |         if (platform_dir.is_dir && !force) {
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 90 |           progress.echo_warning("Platform " + platform + " already installed")
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 91 | } | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 92 |         else {
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 93 |           progress.echo("Platform " + platform + " ...")
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 94 | progress.expose_interrupt() | 
| 79976 | 95 | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 96 |           if (force) {
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 97 |             for (name <- platform.paths) {
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 98 | val dir = component_dir.path + Path.explode(name) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 99 | if (dir.is_dir) Isabelle_System.rm_tree(dir) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 100 | } | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 101 | } | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 102 | |
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 103 | val download = platform.download(base_url, version) | 
| 79976 | 104 | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 105 | val archive_name = | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 106 | Url.get_base_name(download) getOrElse | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 107 |               error("Malformed download URL " + quote(download))
 | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 108 | val archive_path = download_dir + Path.basic(archive_name) | 
| 79976 | 109 | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 110 | Isabelle_System.download_file(download, archive_path) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 111 | Isabelle_System.extract(archive_path, component_dir.path, strip = true) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 112 | Isabelle_System.move_file(component_dir.bin, platform_dir) | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 113 | } | 
| 79976 | 114 | } | 
| 115 | } | |
| 116 | ||
| 117 | File.find_files(component_dir.path.file, pred = file => File.is_exe(file.getName)). | |
| 118 | foreach(file => File.set_executable(File.path(file))) | |
| 119 | ||
| 120 | ||
| 121 | /* README */ | |
| 122 | ||
| 123 | File.write(component_dir.README, | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 124 | """This installation of Go has been produced via "isabelle go_setup". | 
| 79976 | 125 | |
| 126 | ||
| 127 | Makarius | |
| 128 | """ + Date.Format.date(Date.now()) + "\n") | |
| 129 | } | |
| 130 | ||
| 131 | ||
| 132 | /* Isabelle tool wrapper */ | |
| 133 | ||
| 134 | val isabelle_tool = | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 135 |     Isabelle_Tool("go_setup", "dynamic setup of Go component", Scala_Project.here,
 | 
| 79976 | 136 |       { args =>
 | 
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 137 | var target_dir = default_target_dir | 
| 79976 | 138 | var base_url = default_url | 
| 139 | var version = default_version | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 140 | var force = false | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 141 | var platforms = List(default_platform) | 
| 79976 | 142 | |
| 143 |         val getopts = Getopts("""
 | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 144 | Usage: isabelle go_setup [OPTIONS] | 
| 79976 | 145 | |
| 146 | Options are: | |
| 147 | -D DIR target directory (default ".") | |
| 148 | -U URL download URL (default: """" + default_url + """") | |
| 149 | -V VERSION version (default: """" + default_version + """") | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 150 | -f force fresh installation of specified platforms | 
| 80039 | 151 | -p PLATFORMS comma-separated list of platform specifications: "all" or | 
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 152 | as family or formal name (default: """ + quote(default_platform) + """) | 
| 79976 | 153 | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 154 | Download the Go development environment and configure it as Isabelle | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 155 | component. See also https://go.dev | 
| 79976 | 156 | """, | 
| 157 | "D:" -> (arg => target_dir = Path.explode(arg)), | |
| 158 | "U:" -> (arg => base_url = arg), | |
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 159 | "V:" -> (arg => version = arg), | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 160 | "f" -> (_ => force = true), | 
| 80038 | 161 |           "p:" -> (arg => platforms = space_explode(',', arg).map(check_platform)))
 | 
| 79976 | 162 | |
| 163 | val more_args = getopts(args) | |
| 164 | if (more_args.nonEmpty) getopts.usage() | |
| 165 | ||
| 166 | val progress = new Console_Progress() | |
| 167 | ||
| 80011 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 168 | go_setup(platforms = platforms, base_url = base_url, version = version, | 
| 
b082476a8036
dynamic setup of Go component, similar to Dotnet;
 wenzelm parents: 
80008diff
changeset | 169 | target_dir = target_dir, progress = progress, force = force) | 
| 79976 | 170 | }) | 
| 171 | } | |
| 80026 | 172 | |
| 173 | class Go_Setup extends Setup_Tool("go_setup", "ISABELLE_GO_SETUP") {
 | |
| 174 |   override val test_file: Path = Path.explode("lib/Tools/go")
 | |
| 175 | } |