@@ -29,6 +29,7 @@ Available commands are:
29
29
importkeys -- imports signing keys from env
30
30
debsrc [ -signer key-id ] [ -upload dest ] -- creates a debian source package
31
31
nsis -- creates a Windows NSIS installer
32
+ aar [ -sign key-id ] [ -upload dest ] -- creates an android archive
32
33
xgo [ options ] -- cross builds according to options
33
34
34
35
For all commands, -n prevents execution of external programs (dry run mode).
@@ -37,6 +38,7 @@ For all commands, -n prevents execution of external programs (dry run mode).
37
38
package main
38
39
39
40
import (
41
+ "bufio"
40
42
"bytes"
41
43
"encoding/base64"
42
44
"flag"
@@ -48,6 +50,7 @@ import (
48
50
"os"
49
51
"os/exec"
50
52
"path/filepath"
53
+ "regexp"
51
54
"runtime"
52
55
"strings"
53
56
"time"
@@ -125,6 +128,8 @@ func main() {
125
128
doDebianSource (os .Args [2 :])
126
129
case "nsis" :
127
130
doWindowsInstaller (os .Args [2 :])
131
+ case "aar" :
132
+ doAndroidArchive (os .Args [2 :])
128
133
case "xgo" :
129
134
doXgo (os .Args [2 :])
130
135
default :
@@ -331,6 +336,9 @@ func archiveBasename(arch string, env build.Environment) string {
331
336
if arch == "arm" {
332
337
platform += os .Getenv ("GOARM" )
333
338
}
339
+ if arch == "android" {
340
+ platform = "android-all"
341
+ }
334
342
archive := platform + "-" + build .VERSION ()
335
343
if isUnstableBuild (env ) {
336
344
archive += "-unstable"
@@ -630,6 +638,125 @@ func doWindowsInstaller(cmdline []string) {
630
638
if err := archiveUpload (installer , * upload , * signer ); err != nil {
631
639
log .Fatal (err )
632
640
}
641
+
642
+ // Android archives
643
+
644
+ func doAndroidArchive (cmdline []string ) {
645
+ var (
646
+ signer = flag .String ("signer" , "" , `Environment variable holding the signing key (e.g. ANDROID_SIGNING_KEY)` )
647
+ deploy = flag .String ("deploy" , "" , `Where to upload the deploy the archive (usually "https://oss.sonatype.org")` )
648
+ upload = flag .String ("upload" , "" , `Destination to upload the archives (usually "gethstore/builds")` )
649
+ )
650
+ flag .CommandLine .Parse (cmdline )
651
+ env := build .Env ()
652
+
653
+ // Build the Android archive and Maven resources
654
+ build .MustRun (goTool ("get" , "golang.org/x/mobile/cmd/gomobile" ))
655
+ build .MustRun (gomobileTool ("init" ))
656
+ build .MustRun (gomobileTool ("bind" , "--target" , "android" , "--javapkg" , "org.ethereum" , "-v" , "github.com/ethereum/go-ethereum/mobile" ))
657
+
658
+ meta := newMavenMetadata (env )
659
+ build .Render ("build/mvn.pom" , meta .PackageString ()+ ".pom" , 0755 , meta )
660
+
661
+ // Skip Maven deploy and Azure upload for PR builds
662
+ maybeSkipArchive (env )
663
+
664
+ // Sign and upload all the artifacts to Maven Central
665
+ os .Rename ("geth.aar" , meta .PackageString ()+ ".aar" )
666
+ if * signer != "" && * deploy != "" {
667
+ // Import the signing key into the local GPG instance
668
+ if b64key := os .Getenv (* signer ); b64key != "" {
669
+ key , err := base64 .StdEncoding .DecodeString (b64key )
670
+ if err != nil {
671
+ log .Fatalf ("invalid base64 %s" , * signer )
672
+ }
673
+ gpg := exec .Command ("gpg" , "--import" )
674
+ gpg .Stdin = bytes .NewReader (key )
675
+ build .MustRun (gpg )
676
+ }
677
+ // Upload the artifacts to Sonatype and/or Maven Central
678
+ repo := * deploy + "/service/local/staging/deploy/maven2"
679
+ if meta .Unstable {
680
+ repo = * deploy + "/content/repositories/snapshots"
681
+ }
682
+ build .MustRunCommand ("mvn" , "gpg:sign-and-deploy-file" ,
683
+ "-settings=build/mvn.settings" , "-Durl=" + repo , "-DrepositoryId=ossrh" ,
684
+ "-DpomFile=" + meta .PackageString ()+ ".pom" , "-Dfile=" + meta .PackageString ()+ ".aar" )
685
+ }
686
+ // Sign and upload the archive to Azure
687
+ archive := "geth-" + archiveBasename ("android" , env ) + ".aar"
688
+ os .Rename (meta .PackageString ()+ ".aar" , archive )
689
+
690
+ if err := archiveUpload (archive , * upload , * signer ); err != nil {
691
+ log .Fatal (err )
692
+ }
693
+ }
694
+
695
+ func gomobileTool (subcmd string , args ... string ) * exec.Cmd {
696
+ cmd := exec .Command (filepath .Join (GOBIN , "gomobile" ), subcmd )
697
+ cmd .Args = append (cmd .Args , args ... )
698
+ cmd .Env = []string {
699
+ "GOPATH=" + build .GOPATH (),
700
+ }
701
+ for _ , e := range os .Environ () {
702
+ if strings .HasPrefix (e , "GOPATH=" ) {
703
+ continue
704
+ }
705
+ cmd .Env = append (cmd .Env , e )
706
+ }
707
+ return cmd
708
+ }
709
+
710
+ type mavenMetadata struct {
711
+ Env build.Environment
712
+ Version string
713
+ Unstable bool
714
+ Contributors []mavenContributor
715
+ }
716
+
717
+ type mavenContributor struct {
718
+ Name string
719
+ Email string
720
+ }
721
+
722
+ func newMavenMetadata (env build.Environment ) mavenMetadata {
723
+ // Collect the list of authors from the repo root
724
+ contribs := []mavenContributor {}
725
+ if authors , err := os .Open ("AUTHORS" ); err == nil {
726
+ defer authors .Close ()
727
+
728
+ scanner := bufio .NewScanner (authors )
729
+ for scanner .Scan () {
730
+ // Skip any whitespace from the authors list
731
+ line := strings .TrimSpace (scanner .Text ())
732
+ if line == "" || line [0 ] == '#' {
733
+ continue
734
+ }
735
+ // Split the author and insert as a contributor
736
+ re := regexp .MustCompile ("([^<]+) <(.+>)" )
737
+ parts := re .FindStringSubmatch (line )
738
+ if len (parts ) == 3 {
739
+ contribs = append (contribs , mavenContributor {Name : parts [1 ], Email : parts [2 ]})
740
+ }
741
+ }
742
+ }
743
+ return mavenMetadata {
744
+ Env : env ,
745
+ Version : build .VERSION (),
746
+ Unstable : isUnstableBuild (env ),
747
+ Contributors : contribs ,
748
+ }
749
+ }
750
+
751
+ func (meta mavenMetadata ) VersionString () string {
752
+ if meta.Unstable {
753
+ return meta .Version + "-SNAPSHOT"
754
+ }
755
+ return meta .Version
756
+ }
757
+
758
+ func (meta mavenMetadata ) PackageString () string {
759
+ return "geth-" + meta .VersionString ()
633
760
}
634
761
635
762
// Cross compilation
0 commit comments