// NewAPIRouter creates a new HTTP request path router/mux for the given API,
// appContext.
186850
func NewAPIRouter(app *appContext, useRealIP, compressLarge bool) apiMux {
	// chi router
	mux := stackedMux(useRealIP)

	mux.Get("/", app.root)

	mux.Get("/status", app.status)
	mux.Get("/supply", app.coinSupply)

	compMiddleware := m.Next
	if compressLarge {
		log.Debug("Enabling compressed responses for large JSON payload endpoints.")
		compMiddleware = middleware.NewCompressor(3).Handler()
	}

	mux.Route("/block", func(r chi.Router) {
		r.Route("/best", func(rd chi.Router) {
			rd.Use(app.BlockIndexLatestCtx)
			rd.Get("/", app.getBlockSummary) // app.getLatestBlock
			rd.Get("/height", app.currentHeight)
			rd.Get("/hash", app.getBlockHash)
			rd.Route("/header", func(rt chi.Router) {
				rt.Get("/", app.getBlockHeader)
				rt.Get("/raw", app.getBlockHeaderRaw)
			})
			rd.Get("/raw", app.getBlockRaw)
			rd.Get("/size", app.getBlockSize)
			rd.Get("/subsidy", app.blockSubsidies)
			rd.With(compMiddleware).Get("/verbose", app.getBlockVerbose)
			rd.Get("/pos", app.getBlockStakeInfoExtendedByHeight)
			rd.Route("/tx", func(rt chi.Router) {
				rt.Get("/", app.getBlockTransactions)
				rt.Get("/count", app.getBlockTransactionsCount)
			})
		})

		r.Route("/hash/{blockhash}", func(rd chi.Router) {
			rd.Use(app.BlockHashPathAndIndexCtx)
			rd.Get("/", app.getBlockSummary)
			rd.Get("/height", app.getBlockHeight)
			rd.Route("/header", func(rt chi.Router) {
				rt.Get("/", app.getBlockHeader)
				rt.Get("/raw", app.getBlockHeaderRaw)
			})
			rd.Get("/raw", app.getBlockRaw)
			rd.Get("/size", app.getBlockSize)
			rd.Get("/subsidy", app.blockSubsidies)
			rd.With(compMiddleware).Get("/verbose", app.getBlockVerbose)
			rd.Get("/pos", app.getBlockStakeInfoExtendedByHash)
			rd.Route("/tx", func(rt chi.Router) {
				rt.Get("/", app.getBlockTransactions)
				rt.Get("/count", app.getBlockTransactionsCount)
			})
		})

		r.Route("/{idx}", func(rd chi.Router) {
			rd.Use(m.BlockIndexPathCtx)
			rd.Get("/", app.getBlockSummary)
			rd.Route("/header", func(rt chi.Router) {
				rt.Get("/", app.getBlockHeader)
				rt.Get("/raw", app.getBlockHeaderRaw)
			})
			rd.Get("/hash", app.getBlockHash)
			rd.Get("/raw", app.getBlockRaw)
			rd.Get("/size", app.getBlockSize)
			rd.Get("/subsidy", app.blockSubsidies)
			rd.With(compMiddleware).Get("/verbose", app.getBlockVerbose)
			rd.Get("/pos", app.getBlockStakeInfoExtendedByHeight)
			rd.Route("/tx", func(rt chi.Router) {
				rt.Get("/", app.getBlockTransactions)
				rt.Get("/count", app.getBlockTransactionsCount)
			})
		})

		r.Route("/range/{idx0}/{idx}", func(rd chi.Router) {
			rd.Use(m.BlockIndex0PathCtx, m.BlockIndexPathCtx)
			rd.Use(compMiddleware)
			rd.Get("/", app.getBlockRangeSummary)
			rd.Get("/size", app.getBlockRangeSize)
			rd.Route("/{step}", func(rs chi.Router) {
				rs.Use(m.BlockStepPathCtx)
				rs.Get("/", app.getBlockRangeSteppedSummary)
				rs.Get("/size", app.getBlockRangeSteppedSize)
			})
			// rd.Get("/header", app.getBlockHeader)
			// rd.Get("/pos", app.getBlockStakeInfoExtendedByHeight)
		})
	})

	mux.Route("/stake", func(r chi.Router) {
		r.Route("/vote", func(rd chi.Router) {
			rd.Use(app.StakeVersionLatestCtx)
			rd.Get("/info", app.getVoteInfo)
		})
		r.Route("/pool", func(rd chi.Router) {
			rd.With(app.BlockIndexLatestCtx).Get("/", app.getTicketPoolInfo)
			rd.With(app.BlockIndexLatestCtx).Get("/full", app.getTicketPool)
			rd.With(m.BlockIndexPathCtx).Get("/b/{idx}", app.getTicketPoolInfo)
			rd.With(m.BlockIndexOrHashPathCtx).Get("/b/{idxorhash}/full", app.getTicketPool)
			rd.With(m.BlockIndex0PathCtx, m.BlockIndexPathCtx).Get("/r/{idx0}/{idx}", app.getTicketPoolInfoRange)
		})
		r.Route("/diff", func(rd chi.Router) {
			rd.Get("/", app.getStakeDiffSummary)
			rd.Get("/current", app.getStakeDiffCurrent)
			rd.Get("/estimates", app.getStakeDiffEstimates)
			rd.With(m.BlockIndexPathCtx).Get("/b/{idx}", app.getStakeDiff)
			rd.With(m.BlockIndex0PathCtx, m.BlockIndexPathCtx).Get("/r/{idx0}/{idx}", app.getStakeDiffRange)
		})
		r.Get("/powerless", app.getPowerlessTickets)
	})

	mux.Route("/tx", func(r chi.Router) {
		r.Route("/", func(rt chi.Router) {
			rt.Route("/{txid}", func(rd chi.Router) {
				rd.Use(m.TransactionHashCtx)
				rd.Get("/", app.getTransaction)
				rd.Get("/trimmed", app.getDecodedTx)
				rd.Route("/out", func(ro chi.Router) {
					ro.Get("/", app.getTransactionOutputs)
					ro.With(m.TransactionIOIndexCtx).Get("/{txinoutindex}", app.getTransactionOutput)
				})
				rd.Route("/in", func(ri chi.Router) {
					ri.Get("/", app.getTransactionInputs)
					ri.With(m.TransactionIOIndexCtx).Get("/{txinoutindex}", app.getTransactionInput)
				})
				rd.Get("/vinfo", app.getTxVoteInfo)
				rd.Get("/tinfo", app.getTxTicketInfo)
			})
		})
		r.With(m.TransactionHashCtx).Get("/hex/{txid}", app.getTransactionHex)
		r.With(m.TransactionHashCtx).Get("/decoded/{txid}", app.getDecodedTx)
	})

	mux.Route("/txs", func(r chi.Router) {
		r.Use(middleware.AllowContentType("application/json"),
			m.ValidateTxnsPostCtx, m.PostTxnsCtx)
		r.Post("/", app.getTransactions)
		r.Post("/trimmed", app.getDecodedTransactions)
	})

	mux.Route("/address", func(r chi.Router) {
		r.Route("/{address}", func(rd chi.Router) {
			rd.Use(m.AddressPathCtx)
			rd.Get("/totals", app.addressTotals)
			rd.Get("/", app.getAddressTransactions)
			rd.With(m.ChartGroupingCtx).Get("/types/{chartgrouping}", app.getAddressTxTypesData)
			rd.With(m.ChartGroupingCtx).Get("/amountflow/{chartgrouping}", app.getAddressTxAmountFlowData)
			rd.With(compMiddleware).Get("/raw", app.getAddressTransactionsRaw)
			rd.Route("/count/{N}", func(ri chi.Router) {
				ri.Use(m.NPathCtx)
				ri.Get("/", app.getAddressTransactions)
				ri.With(compMiddleware).Get("/raw", app.getAddressTransactionsRaw)
				ri.Route("/skip/{M}", func(rj chi.Router) {
					rj.Use(m.MPathCtx)
					rj.Get("/", app.getAddressTransactions)
					rj.With(compMiddleware).Get("/raw", app.getAddressTransactionsRaw)
				})
			})
		})
	})

	// Returns agenda data like; description, name, lockedin activated and other
	// high level agenda details for all agendas.
	mux.Route("/agendas", func(r chi.Router) {
		r.Get("/", app.getAgendasData)
	})

	// Returns the charts data for the respective individual agendas.
	mux.Route("/agenda", func(r chi.Router) {
		r.With(m.AgendIdCtx).Get("/{agendaId}", app.getAgendaData)
	})

	mux.Route("/mempool", func(r chi.Router) {
		r.Get("/", http.NotFound /*app.getMempoolOverview*/)
		// ticket purchases
		r.Route("/sstx", func(rd chi.Router) {
			rd.Get("/", app.getSSTxSummary)
			rd.Get("/fees", app.getSSTxFees)
			rd.With(m.NPathCtx).Get("/fees/{N}", app.getSSTxFees)
			rd.Get("/details", app.getSSTxDetails)
			rd.With(m.NPathCtx).Get("/details/{N}", app.getSSTxDetails)
		})
	})

	mux.Route("/chart", func(r chi.Router) {
		// Return default chart data (ticket price)
		r.Route("/market/{token}", func(rd chi.Router) {
			rd.Use(m.ExchangeTokenContext)
			rd.With(m.StickWidthContext).Get("/candlestick/{bin}", app.getCandlestickChart)
			rd.Get("/depth", app.getDepthChart)
		})
		r.With(m.ChartTypeCtx).Get("/{charttype}", app.ChartTypeData)
	})

	mux.Route("/ticketpool", func(r chi.Router) {
		r.Get("/", app.getTicketPoolByDate)
		r.With(m.TicketPoolCtx).Get("/bydate/{tp}", app.getTicketPoolByDate)
		r.Get("/charts", app.getTicketPoolCharts)
	})

	mux.Route("/proposal", func(r chi.Router) {
		r.With(m.ProposalTokenCtx).Get("/{token}", app.getProposalChartData)
	})

	mux.Route("/exchanges", func(r chi.Router) {
		r.Get("/", app.getExchanges)
		r.Get("/codes", app.getCurrencyCodes)
	})

	mux.NotFound(func(w http.ResponseWriter, r *http.Request) {
		http.Error(w, r.URL.RequestURI()+" ain't no country I've ever heard of! (404)", http.StatusNotFound)
	})

	// if cfg.PrintAPIDirectory {
	// 	var buf bytes.Buffer
	// 	json.Indent(&buf, []byte(docgen.JSONRoutesDoc(mux)), "", "\t")
	// 	buf.WriteTo(os.Stdout)

	// 	fmt.Println(docgen.MarkdownRoutesDoc(mux, docgen.MarkdownOpts{
	// 		ProjectPath: "github.com/decred/dcrdata/v5",
	// 		Intro:       "dcrdata HTTP router directory",
	// 	}))
	// 	return
	// }

	// mux.HandleFunc("/directory", APIDirectory)
	// mux.With(apiDocs(mux)).HandleFunc("/directory", APIDirectory)

	var listRoutePatterns func(routes []chi.Route) []string
	listRoutePatterns = func(routes []chi.Route) []string {
		patterns := []string{}
		for _, rt := range routes {
			patterns = append(patterns, strings.Replace(rt.Pattern, "/*", "", -1))
			if rt.SubRoutes == nil {
				continue
			}
			for _, pt := range listRoutePatterns(rt.SubRoutes.Routes()) {
				patterns = append(patterns, strings.Replace(rt.Pattern+pt, "/*", "", -1))
			}
		}
		return patterns
	}

	mux.HandleFunc("/list", app.writeJSONHandlerFunc(listRoutePatterns(mux.Routes())))

	return apiMux{mux}
}
482722
func (c *CommandBase) NewAPIRoot(
	store jujuclient.ClientStore,
	controllerName, modelName string,
) (api.Connection, error) {
	c.assertRunStarted()
	accountDetails, err := store.AccountDetails(controllerName)
	if err != nil && !errors.IsNotFound(err) {
		return nil, errors.Trace(err)
	}
	// If there are no account details or there's no logged-in
	// user or the user is external, then trigger macaroon authentication
	// by using an empty AccountDetails.
	if accountDetails == nil || accountDetails.User == "" {
		accountDetails = &jujuclient.AccountDetails{}
	} else {
		u := names.NewUserTag(accountDetails.User)
		if !u.IsLocal() {
			accountDetails = &jujuclient.AccountDetails{}
		}
	}
	param, err := c.NewAPIConnectionParams(
		store, controllerName, modelName, accountDetails,
	)
	if err != nil {
		return nil, errors.Trace(err)
	}
	conn, err := juju.NewAPIConnection(param)
	if modelName != "" && params.ErrCode(err) == params.CodeModelNotFound {
		return nil, c.missingModelError(store, controllerName, modelName)
	}
	if redirErr, ok := errors.Cause(err).(*api.RedirectError); ok {
		return nil, c.modelMigratedError(store, modelName, redirErr)
	}

	return conn, err
}
35042
func NewControllerAPIv3(ctx facade.Context) (*ControllerAPIv3, error) {
	v4, err := NewControllerAPIv4(ctx)
	if err != nil {
		return nil, errors.Trace(err)
	}
	return &ControllerAPIv3{v4}, nil
}
351957
func newContext(ctx context.Context, e events.APIGatewayProxyRequest) context.Context {
	return context.WithValue(ctx, requestContextKey, e.RequestContext)
}
675555
func NewAPI(ctx facade.Context) (*API, error) {
	if !ctx.Auth().AuthController() {
		return nil, common.ErrPerm
	}

	return &API{}, nil
}
457144
func NewAPIHandler(b *APIBackend) *APIHandler {
	h := &APIHandler{}
	sessionBackend := NewSessionBackend(b)
	h.SessionHandler = NewSessionHandler(sessionBackend)

	h.BucketHandler = NewBucketHandler(b.UserResourceMappingService, b.LabelService, b.UserService)
	h.BucketHandler.BucketService = b.BucketService
	h.BucketHandler.BucketOperationLogService = b.BucketOperationLogService

	h.OrgHandler = NewOrgHandler(b.UserResourceMappingService, b.LabelService, b.UserService)
	h.OrgHandler.OrganizationService = b.OrganizationService
	h.OrgHandler.BucketService = b.BucketService
	h.OrgHandler.OrganizationOperationLogService = b.OrganizationOperationLogService
	h.OrgHandler.SecretService = b.SecretService

	h.UserHandler = NewUserHandler()
	h.UserHandler.UserService = b.UserService
	h.UserHandler.BasicAuthService = b.BasicAuthService
	h.UserHandler.UserOperationLogService = b.UserOperationLogService

	h.DashboardHandler = NewDashboardHandler(b.UserResourceMappingService, b.LabelService, b.UserService)
	h.DashboardHandler.DashboardService = b.DashboardService
	h.DashboardHandler.DashboardOperationLogService = b.DashboardOperationLogService

	h.MacroHandler = NewMacroHandler()
	h.MacroHandler.MacroService = b.MacroService

	h.AuthorizationHandler = NewAuthorizationHandler(b.UserService)
	h.AuthorizationHandler.OrganizationService = b.OrganizationService
	h.AuthorizationHandler.AuthorizationService = b.AuthorizationService
	h.AuthorizationHandler.LookupService = b.LookupService
	h.AuthorizationHandler.Logger = b.Logger.With(zap.String("handler", "auth"))

	h.SourceHandler = NewSourceHandler()
	h.SourceHandler.SourceService = b.SourceService
	h.SourceHandler.NewBucketService = b.NewBucketService
	h.SourceHandler.NewQueryService = b.NewQueryService

	h.SetupHandler = NewSetupHandler()
	h.SetupHandler.OnboardingService = b.OnboardingService

	h.TaskHandler = NewTaskHandler(b.UserResourceMappingService, b.LabelService, b.Logger, b.UserService)
	h.TaskHandler.TaskService = b.TaskService
	h.TaskHandler.AuthorizationService = b.AuthorizationService
	h.TaskHandler.UserResourceMappingService = b.UserResourceMappingService

	h.TelegrafHandler = NewTelegrafHandler(
		b.Logger.With(zap.String("handler", "telegraf")),
		b.UserResourceMappingService,
		b.LabelService,
		b.TelegrafService,
		b.UserService,
	)

	h.WriteHandler = NewWriteHandler(b.PointsWriter)
	h.WriteHandler.OrganizationService = b.OrganizationService
	h.WriteHandler.BucketService = b.BucketService
	h.WriteHandler.Logger = b.Logger.With(zap.String("handler", "write"))

	h.QueryHandler = NewFluxHandler()
	h.QueryHandler.OrganizationService = b.OrganizationService
	h.QueryHandler.Logger = b.Logger.With(zap.String("handler", "query"))
	h.QueryHandler.ProxyQueryService = b.ProxyQueryService

	h.ProtoHandler = NewProtoHandler(NewProtoBackend(b))

	h.ChronografHandler = NewChronografHandler(b.ChronografService)

	return h
}
631240
func (c *ControllerCommandBase) NewModelAPIRoot(modelName string) (api.Connection, error) {
	controllerName, err := c.ControllerName()
	if err != nil {
		return nil, errors.Trace(err)
	}
	_, err = c.store.ModelByName(controllerName, modelName)
	if err != nil {
		if !errors.IsNotFound(err) {
			return nil, errors.Trace(err)
		}
		// The model isn't known locally, so query the models
		// available in the controller, and cache them locally.
		if err := c.RefreshModels(c.store, controllerName); err != nil {
			return nil, errors.Annotate(err, "refreshing models")
		}
	}
	return c.newAPIRoot(modelName)
}
64796
func NewEndpointPath(application, name string) string {
	return fmt.Sprintf(HTTPEndpointPath, application, name)
}
929409
func NewAPIClient(apiCaller base.APICallCloser) (*client.Client, error) {
	caller := base.NewFacadeCallerForVersion(apiCaller, resource.FacadeName, 1)

	httpClient, err := apiCaller.HTTPClient()
	if err != nil {
		return nil, errors.Trace(err)
	}
	// The apiCaller takes care of prepending /environment/<modelUUID>.
	apiClient := client.NewClient(caller, httpClient, apiCaller)
	return apiClient, nil
}
10573
func NewControllerAPIv6(ctx facade.Context) (*ControllerAPIv6, error) {
	v7, err := NewControllerAPIv7(ctx)
	if err != nil {
		return nil, errors.Trace(err)
	}
	return &ControllerAPIv6{v7}, nil
}
1221282
func NewAPIClient(cli common.RCHTTPClienter, url string) (api *Client) {
	return &Client{
		HTTPClient: cli,
		BaseURL:    url,
	}
}
435702
func newAPIHandler(srv *Server, st *state.State, rpcConn *rpc.Conn, modelUUID string, connectionID uint64, serverHost string) (*apiHandler, error) {
	m, err := st.Model()
	if err != nil {
		if !errors.IsNotFound(err) {
			return nil, errors.Trace(err)
		}

		// If this model used to be hosted on this controller but got
		// migrated allow clients to connect and wait for a login
		// request to decide whether the users should be redirected to
		// the new controller for this model or not.
		if _, migErr := st.LatestRemovedModelMigration(); migErr != nil {
			return nil, errors.Trace(err) // return original NotFound error
		}
	}

	r := &apiHandler{
		state:        st,
		model:        m,
		resources:    common.NewResources(),
		shared:       srv.shared,
		rpcConn:      rpcConn,
		modelUUID:    modelUUID,
		connectionID: connectionID,
		serverHost:   serverHost,
	}

	if err := r.resources.RegisterNamed("machineID", common.StringResource(srv.tag.Id())); err != nil {
		return nil, errors.Trace(err)
	}
	if err := r.resources.RegisterNamed("dataDir", common.StringResource(srv.dataDir)); err != nil {
		return nil, errors.Trace(err)
	}
	if err := r.resources.RegisterNamed("logDir", common.StringResource(srv.logDir)); err != nil {
		return nil, errors.Trace(err)
	}

	// Facades involved with managing application offers need the auth context
	// to mint and validate macaroons.
	localOfferAccessEndpoint := url.URL{
		Scheme: "https",
		Host:   serverHost,
		Path:   localOfferAccessLocationPath,
	}
	offerAuthCtxt := srv.offerAuthCtxt.WithDischargeURL(localOfferAccessEndpoint.String())
	if err := r.resources.RegisterNamed(
		"offerAccessAuthContext",
		common.ValueResource{Value: offerAuthCtxt},
	); err != nil {
		return nil, errors.Trace(err)
	}
	return r, nil
}
523628
func NewRouter() *mux.Router {
	r := transport.NewAPIRouter()

	// All old versions are deprecated in the daemon. Use an up to
	// date client!
	transport.DeprecateVersions(r, "v1", "v2", "v3", "v4", "v5")
	// We assume every request that doesn't match a route is a client
	// calling an old or hitherto unsupported API.
	r.NewRoute().Name("NotFound").HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
		transport.WriteError(w, r, http.StatusNotFound, transport.MakeAPINotFound(r.URL.Path))
	})

	return r
}
321498
func NewAPI(opts ...apiOption) (*API, error) {
	api := &API{}

	for _, opt := range opts {
		err := opt(api)
		if err != nil {
			return nil, errors.Wrap(err, "applying option")
		}
	}
	return api, nil
}
423045
func NewHTTPProvider(path string) (*HTTPProvider, error) {
	if _, err := os.Stat(path); os.IsNotExist(err) {
		return nil, fmt.Errorf("webroot path does not exist")
	}

	return &HTTPProvider{path: path}, nil
}
80208
func New(ctx interface{}) *Router {
	validateContext(ctx, nil)

	r := &Router{}
	r.contextType = reflect.TypeOf(ctx)
	r.pathPrefix = "/"
	r.maxChildrenDepth = 1
	r.root = make(map[httpMethod]*pathNode)
	for _, method := range httpMethods {
		r.root[method] = newPathNode()
	}
	return r
}
88224
func New(opts ...OptionFunc) *HTTPBin {
	h := &HTTPBin{
		MaxBodySize: DefaultMaxBodySize,
		MaxDuration: DefaultMaxDuration,
	}
	for _, opt := range opts {
		opt(h)
	}
	return h
}