| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | package main | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | import ( | 
					
						
							|  |  |  | 	"flag" | 
					
						
							|  |  |  | 	"fmt" | 
					
						
							| 
									
										
										
										
											2020-05-10 21:22:40 +00:00
										 |  |  | 	"io/ioutil" | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 	"log" | 
					
						
							| 
									
										
										
										
											2020-08-01 07:32:17 +00:00
										 |  |  | 	"math/rand" | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 	"net/http" | 
					
						
							| 
									
										
										
										
											2019-08-13 23:35:56 +00:00
										 |  |  | 	"net/url" | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 	"os" | 
					
						
							|  |  |  | 	"strconv" | 
					
						
							| 
									
										
										
										
											2020-08-01 07:32:17 +00:00
										 |  |  | 	"time" | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-04-10 19:41:10 +00:00
										 |  |  | 	"git.coolaj86.com/coolaj86/go-mockid/mockid" | 
					
						
							| 
									
										
										
										
											2020-05-11 04:40:46 +00:00
										 |  |  | 	"git.rootprojects.org/root/keypairs" | 
					
						
							| 
									
										
										
										
											2019-08-19 03:34:19 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-04-10 19:41:10 +00:00
										 |  |  | 	_ "github.com/joho/godotenv/autoload" | 
					
						
							| 
									
										
										
										
											2020-04-10 19:29:01 +00:00
										 |  |  | ) | 
					
						
							| 
									
										
										
										
											2019-08-19 05:04:55 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | func main() { | 
					
						
							|  |  |  | 	done := make(chan bool) | 
					
						
							|  |  |  | 	var port int | 
					
						
							| 
									
										
										
										
											2019-08-13 23:35:56 +00:00
										 |  |  | 	var host string | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-08-01 07:32:17 +00:00
										 |  |  | 	rand.Seed(time.Now().UnixNano()) | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 	portFlag := flag.Int("port", 0, "Port on which the HTTP server should run") | 
					
						
							| 
									
										
										
										
											2019-08-13 23:35:56 +00:00
										 |  |  | 	urlFlag := flag.String("url", "", "Outward-facing address, such as https://example.com") | 
					
						
							| 
									
										
										
										
											2019-08-19 03:34:19 +00:00
										 |  |  | 	prefixFlag := flag.String("jwkspath", "", "The path to the JWKs storage directory") | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 	flag.Parse() | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	if nil != portFlag && *portFlag > 0 { | 
					
						
							|  |  |  | 		port = *portFlag | 
					
						
							|  |  |  | 	} else { | 
					
						
							|  |  |  | 		portStr := os.Getenv("PORT") | 
					
						
							|  |  |  | 		port, _ = strconv.Atoi(portStr) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 	if port < 1 { | 
					
						
							|  |  |  | 		fmt.Fprintf(os.Stderr, "You must specify --port or PORT\n") | 
					
						
							|  |  |  | 		os.Exit(1) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-05-10 21:22:40 +00:00
										 |  |  | 	jwkpath := "./default.jwk.json" | 
					
						
							|  |  |  | 	jwkb, err := ioutil.ReadFile(jwkpath) | 
					
						
							|  |  |  | 	if nil != err { | 
					
						
							|  |  |  | 		panic(fmt.Errorf("read default jwk %v: %w", jwkpath, err)) | 
					
						
							|  |  |  | 		return | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-05-11 04:40:46 +00:00
										 |  |  | 	privkey, err := keypairs.ParseJWKPrivateKey(jwkb) | 
					
						
							| 
									
										
										
										
											2020-05-10 21:22:40 +00:00
										 |  |  | 	if nil != err { | 
					
						
							|  |  |  | 		// TODO delete the bad file? | 
					
						
							|  |  |  | 		panic(fmt.Errorf("unmarshal jwk %v: %w", string(jwkb), err)) | 
					
						
							|  |  |  | 		return | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2019-08-13 23:35:56 +00:00
										 |  |  | 	if nil != urlFlag && "" != *urlFlag { | 
					
						
							|  |  |  | 		host = *urlFlag | 
					
						
							|  |  |  | 	} else { | 
					
						
							|  |  |  | 		host = "http://localhost:" + strconv.Itoa(port) | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-04-10 19:41:10 +00:00
										 |  |  | 	var jwksPrefix string | 
					
						
							| 
									
										
										
										
											2019-08-19 03:34:19 +00:00
										 |  |  | 	if nil != prefixFlag && "" != *prefixFlag { | 
					
						
							|  |  |  | 		jwksPrefix = *prefixFlag | 
					
						
							|  |  |  | 	} else { | 
					
						
							|  |  |  | 		jwksPrefix = "public-jwks" | 
					
						
							|  |  |  | 	} | 
					
						
							| 
									
										
										
										
											2020-05-10 21:22:40 +00:00
										 |  |  | 	err = os.MkdirAll(jwksPrefix, 0755) | 
					
						
							| 
									
										
										
										
											2019-08-19 03:34:19 +00:00
										 |  |  | 	if nil != err { | 
					
						
							|  |  |  | 		fmt.Fprintf(os.Stderr, "couldn't write %q: %s", jwksPrefix, err) | 
					
						
							|  |  |  | 		os.Exit(1) | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-07-25 09:13:19 +00:00
										 |  |  | 	mux := mockid.Route(jwksPrefix, privkey) | 
					
						
							| 
									
										
										
										
											2019-08-19 03:34:19 +00:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-05-10 21:22:40 +00:00
										 |  |  | 	fs := http.FileServer(http.Dir("./public")) | 
					
						
							| 
									
										
										
										
											2019-08-13 23:35:56 +00:00
										 |  |  | 	http.Handle("/", fs) | 
					
						
							|  |  |  | 	/* | 
					
						
							|  |  |  | 		http.HandleFunc("/", func(w http.ResponseWriter, r *http.Request) { | 
					
						
							|  |  |  | 			log.Printf(r.Method, r.URL.Path) | 
					
						
							|  |  |  | 			http.Error(w, "Not Found", http.StatusNotFound) | 
					
						
							|  |  |  | 		}) | 
					
						
							|  |  |  | 	*/ | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 
 | 
					
						
							|  |  |  | 	fmt.Printf("Serving on port %d\n", port) | 
					
						
							|  |  |  | 	go func() { | 
					
						
							| 
									
										
										
										
											2020-07-25 09:13:19 +00:00
										 |  |  | 		log.Fatal(http.ListenAndServe(":"+strconv.Itoa(port), mux)) | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 		done <- true | 
					
						
							|  |  |  | 	}() | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-05-11 04:40:46 +00:00
										 |  |  | 	// TODO privB := keypairs.MarshalJWKPrivateKey(privkey) | 
					
						
							| 
									
										
										
										
											2022-05-05 17:38:25 -06:00
										 |  |  | 	privB := keypairs.MarshalJWKPrivateKey(privkey) | 
					
						
							| 
									
										
										
										
											2020-05-11 04:40:46 +00:00
										 |  |  | 	fmt.Printf("Private Key:\n\t%s\n", string(privB)) | 
					
						
							|  |  |  | 	pubB := keypairs.MarshalJWKPublicKey(keypairs.NewPublicKey(privkey.Public())) | 
					
						
							|  |  |  | 	fmt.Printf("Public Key:\n\t%s\n", string(pubB)) | 
					
						
							|  |  |  | 	protected, payload, token := mockid.GenToken(host, privkey, url.Values{}) | 
					
						
							| 
									
										
										
										
											2019-08-01 06:21:32 +00:00
										 |  |  | 	fmt.Printf("Protected (Header):\n\t%s\n", protected) | 
					
						
							|  |  |  | 	fmt.Printf("Payload (Claims):\n\t%s\n", payload) | 
					
						
							|  |  |  | 	fmt.Printf("Access Token:\n\t%s\n", token) | 
					
						
							|  |  |  | 
 | 
					
						
							|  |  |  | 	<-done | 
					
						
							|  |  |  | } |