{"owner":"goharbor","repo":"harbor","hasSkills":true,"totalSkillsCount":2,"totalTokensCount":2946,"categories":["plugin-manifest"],"hasMcp":false,"mcpConfig":null,"found":["tools/swagger/templates/README.md","tools/migrate_chart/Readme.md"],"skills":{"tools/swagger/templates/README.md":"# swagger\n\nIn Stratoscale, we really like the idea of API-first services, and we also really like Go.\nWe saw the go-swagger library, and thought that most of it can really help us. Generating code from\nswagger files is a big problem with a lot of corner cases, and go-swagger is doing great job.\n\nThe one thing that we felt missing was customization of the server to run with our design principles:\n\n* Custom `main` function\n* Dependency injection\n* Limited scope with unit testing.\n\nAlso:\n\n* Adding your functions to the generated `configure_swagger_*.go` seems to be a burden.\n* Lack of Interface that the service implements.\n* Complicated and custom http clients and runtime.\n\nThose are the changes that this contributor templates are providing:\n\n## Server\n\n### The new `restapi` package exposes interfaces\n\n* Those interfaces can be implemented by the developer and are the business logic of the service.\n* The implementation of those is extensible.\n* The implementation is separated from the generated code.\n\n### The `restapi` returns an `http.Handler`\n\nThe `restapi.Handler` (see [example](./example/restapi/configure_swagger_petstore.go)) function returns\na standard `http.Handler`\n\n* Given objects that implements the business logic, we can create a simple http handler.\n* This handler is a standard go http.Handler, so we can now use any other middleware, library, or framework\nthat supports it.\n* This handler is standard, so we understand it better.\n\n## Client\n\n* The new client package exposes interfaces, so functions in our code can receive those\n  interfaces which can be mocked for testing.\n* The new client has a config that gets an `*url.URL` to customize the endpoint.\n* The new client has a config that gets an `http.RoundTripper` to customize client with libraries, middleware or\n  frameworks that support the standard library's objects.\n\n# Example Walk-Through\n\nIn the [example package](https://github.com/Stratoscale/swagger/tree/master/example) you'll find generated code and usage of the pet-store\n[swagger file](./example/swagger.yaml).\n\n* The `restapi`, `models` and `client` are auto-generated by the stratoscale/swagger docker file.\n* The `internal` package was manually added and contains the server's business logic.\n* The `main.go` file is the entrypoint and contains initializations and dependency injections of the project.\n\n## Server\n\n### [restapi](https://github.com/Stratoscale/swagger/tree/master/example/restapi)\n\nThis package is autogenerated and contains the server routing and parameter parsing.\n\nThe modified version contains `restapi.PetAPI` and `restapi.StoreAPI` which were auto generated.\n\n```go\n// PetAPI\ntype PetAPI interface {\n\tPetCreate(ctx context.Context, params pet.PetCreateParams) middleware.Responder\n\tPetDelete(ctx context.Context, params pet.PetDeleteParams) middleware.Responder\n\tPetGet(ctx context.Context, params pet.PetGetParams) middleware.Responder\n\tPetList(ctx context.Context, params pet.PetListParams) middleware.Responder\n\tPetUpdate(ctx context.Context, params pet.PetUpdateParams) middleware.Responder\n}\n\n//go:generate mockery -name StoreAPI -inpkg\n\n// StoreAPI\ntype StoreAPI interface {\n\tInventoryGet(ctx context.Context, params store.InventoryGetParams) middleware.Responder\n\tOrderCreate(ctx context.Context, params store.OrderCreateParams) middleware.Responder\n\t// OrderDelete is For valid response try integer IDs with positive integer value. Negative or non-integer values will generate API errors\n\tOrderDelete(ctx context.Context, params store.OrderDeleteParams) middleware.Responder\n\t// OrderGet is For valid response try integer IDs with value >= 1 and <= 10. Other values will generated exceptions\n\tOrderGet(ctx context.Context, params store.OrderGetParams) middleware.Responder\n}\n```\n\nEach function matches an `operationId` in the swagger file and they are grouped according to\nthe operation `tags`.\n\nThere is also a `restapi.Config`:\n\n```go\n// Config is configuration for Handler\ntype Config struct {\n\tPetAPI\n\tStoreAPI\n\tLogger func(string, ...any)\n\t// InnerMiddleware is for the handler executors. These do not apply to the swagger.json document.\n\t// The middleware executes after routing but before authentication, binding and validation\n\tInnerMiddleware func(http.Handler) http.Handler\n}\n```\n\nThis config is auto generated and contains all the declared interfaces above.\nIt is used to initiate an http.Handler with the `Handler` function:\n\n```go\n// Handler returns an http.Handler given the handler configuration\n// It mounts all the business logic implementers in the right routing.\nfunc Handler(c Config) (http.Handler, error) {\n    ...\n```\n\nLet's look how we use this generated code to build our server.\n\n### [internal](https://github.com/Stratoscale/swagger/tree/master/example/internal)\n\nThe `internal` package is **not** auto generated and contains the business logic of our server.\nWe can see two structs that implement the `restapi.PetAPI` and `restapi.StoreAPI` interfaces,\nneeded to make our server work.\n\nWhen adding or removing functions from our REST API, we can just add or remove functions to those\nbusiness logic units. We can also create new logical units when they are added to our REST API.\n\n### [main.go](./example/main.go)\n\nThe main function is pretty straight forward. We initiate our business logic units.\nThen create a config for our rest API. We then create a standard `http.Handler` which we can\nupdate with middleware, test with `httptest`, or to use with other standard tools.\nThe last piece is to run the handler with `http.ListenAndServe` or to use it with an `http.Server` -\nit is all very customizable.\n\n```go\nfunc main() {\n\t// Initiate business logic implementers.\n\t// This is the main function, so here the implementers' dependencies can be\n\t// injected, such as database, parameters from environment variables, or different\n\t// clients for different APIs.\n\tp := internal.Pet{}\n\ts := internal.Store{}\n\n\t// Initiate the http handler, with the objects that are implementing the business logic.\n\th, err := restapi.Handler(restapi.Config{\n\t\tPetAPI:   &p,\n\t\tStoreAPI: &s,\n\t\tLogger:   log.Printf,\n\t})\n\tif err != nil {\n\t\tlog.Fatal(err)\n\t}\n\n\t// Run the standard http server\n\tlog.Fatal(http.ListenAndServe(\":8080\", h))\n}\n```\n\n## Client\n\nThe client code is in the [client package](https://github.com/Stratoscale/swagger/tree/master/example/client) and is autogenerated.\n\nTo create a new client we use the `client.Config` struct:\n\n```go\ntype Config struct {\n\t// URL is the base URL of the upstream server\n\tURL *url.URL\n\t// Transport is an inner transport for the client\n\tTransport http.RoundTripper\n}\n```\n\nThis enables us to use custom server endpoint or custom client middleware. Easily, with the\nstandard components, and with any library that accepts them.\n\nThe client is then generated with the New method:\n\n```go\n// New creates a new swagger petstore HTTP client.\nfunc New(c Config) *SwaggerPetstore { ... }\n```\n\nThis method returns an object that has two important fields:\n\n```go\ntype SwaggerPetstore {\n\t...\n\tPet       *pet.Client\n\tStore     *store.Client\n}\n```\n\nThose fields are objects, which implement interfaces declared in the [pet](./example/client/pet) and\n[store](./example/client/store) packages:\n\nFor example:\n\n```go\n// API is the interface of the pet client\ntype API interface {\n\t// PetCreate adds a new pet to the store\n\tPetCreate(ctx context.Context, params *PetCreateParams) (*PetCreateCreated, error)\n\t// PetDelete deletes a pet\n\tPetDelete(ctx context.Context, params *PetDeleteParams) (*PetDeleteNoContent, error)\n\t// PetGet gets pet by it s ID\n\tPetGet(ctx context.Context, params *PetGetParams) (*PetGetOK, error)\n\t// PetList lists pets\n\tPetList(ctx context.Context, params *PetListParams) (*PetListOK, error)\n\t// PetUpdate updates an existing pet\n\tPetUpdate(ctx context.Context, params *PetUpdateParams) (*PetUpdateCreated, error)\n}\n```\n\nThey are very similar to the server interfaces, and can be used by consumers of those APIs\n(instead of using the actual client or the `*Pet` struct)\n\n# Authentication\n\nAuthenticating and policy enforcement of the application is done in several stages, described below.\n\n## Define security in swagger.yaml\n\nAdd to the root of the swagger.yaml the security and security definitions sections.\n\n```yaml\nsecurityDefinitions:\n  token:\n    type: apiKey\n    in: header\n    name: Cookie\n\nsecurity:\n  - token: []\n```\n\nThe securityDefinitions section defines different security types that your application can handle.\nThe supported types by go-swagger are:\n* `apiKey` - token that should be able to be processed.\n* `oauth2` - token and scopes that should be processed. \n* and `basic` - user/password that should be processed.\n\nHere we defined an apiKey, that is passed through the Cookie header.\n\nThe `security` section defines the default security enforcement for the application. You can select\ndifferent securityDefinitions, as the keys, and apply \"scopes\" as the values. Those default definitions\ncan be overridden in each route by a section with the same name:\n\n```yaml\npaths:\n  /pets:\n    post:\n      [...]\n      security:\n        - token: [admin]\n```\n\nHere we have overridden the scope of the token in the POST /pets URL so that only admin can use this API.\n\nLet's see how we can use this functionality.\n\n## Writing Security Handlers\n\nOnce we created a security definition named \"token\", a function called \"AuthToken\" was added to the `restapi.Config`:\n\n```go\ntype Config struct {\n    ...\n\t// AuthToken Applies when the \"Cookie\" header is set\n\tAuthToken func(token string) (any, error)\n}\n```\n\nThis function gets the content of the Cookie header, and should return an `any` and `error`.\nThe `any` is the object that should represent the user that performed the request, it should\nbe nil to return an unauthorized 401 HTTP response. If the returned `error` is not nil, an HTTP 500,\ninternal server error will be returned.\n\nThe returned object, will be stored in the request context under the `restapi.AuthKey` key.\n\nThere is another function that we should know about, in the `restapi.Config` struct:\n\n```go\ntype Config struct {\n\t...\n\t// Authorizer is used to authorize a request after the Auth function was called using the \"Auth*\" functions\n\t// and the principal was stored in the context in the \"AuthKey\" context value.\n\tAuthorizer func(*http.Request) error\n}\n```\n\nThis one is a custom defined function that gets the request and can return an error.\nIf the returned error is not nil, and 403 HTTP error will be returned to the client - here the policy\nenforcement comes into play.\nThere are two things that this function should be aware of:\n\n1. The user - it can retrieve the user information from the context: `ctx.Value(restapi.AuthKey).(MyUserType)`.\n   Usually, a server will have a function for extracting this user information and returns a concrete\n   type which could be used by all the routes.\n2. The route - it can retrieve the route using the go-swagger function: `middleware.MatchedRouteFrom(*http.Request)`.\n   So no need to parse the URL and test the request method.\n   This route struct contains the route information. If for example, we want to check the scopes that were\n   defined for the current route in the swagger.yaml we can use the code below:\n   \n```go\nfor _, auth := range route.Authenticators {\n    for scopeName, scopeValues := range auth.Scopes {\n        for _, scopeValue := range scopeValues {\n            ...\n        }\n    }\n}\n```\n","tools/migrate_chart/Readme.md":"# Chart Migrating Tool\n\nHarbor supports two different ways to storage the chart data.\n\n   1. stored in Harbor registry storage directly via OCI API.\n   2. stored in Harbor hosted chartmuseum backend via chartmuseam's API\n\nThere is an performance issue in chartmuseam. For example, on my 2 core 8G memory test environment, to get 10000 charts information needs about 10s to return, In 50000 charts situation, It will cause a timeout error.\n\nAfter version 2.0, Harbor becomes to the OCI registry. So It can storage chart content directly without chartmuseum.\n\nThis tool used to migrate the legacy helm charts stored in the chartmuseum backend to Harbor OCI registry backend.\n\nOn test environment( 2 core 8G memory), using this tool to migrate 10000 charts needs about 2~3 hours\n\n## Usages\n\nCompile the chart with command\n\n``` sh\ndocker build -t goharbor/migrate-chart:0.1.0 .\n```\n\nMigrate charts run command below:\n\n``` sh\ndocker run -it --rm -v {{your_chart_data_location}}:/chart_storage -v {{harbor_ca_cert_location}}:/usr/local/share/ca-certificates/harbor_ca.crt  goharbor/migrate-chart:0.1.0 --hostname {{harbor_hostname}} --password {{harbor_admin_password}}\n```\n\n* `your_chart_data_location`: The location of your chart storage chart. By default, it's the `chart_storage` dir inside Harbor's `data_volumn`\n\n* `harbor_ca_cert_location`: If Harbor enabled HTTPS, you need to add the `ca_cert` for connecting Harbor\n\n* `harbor_hostname`: The hostname of Harbor\n\n* `harbor_admin_password`: The password of harbor admin user\n"},"files":{"tools/swagger/templates/README.md":"# swagger\n\nIn Stratoscale, we really like the idea of API-first services, and we also really like Go.\nWe saw the go-swagger library, and thought that most of it can really help us. Generating code from\nswagger files is a big problem with a lot of corner cases, and go-swagger is doing great job.\n\nThe one thing that we felt missing was customization of the server to run with our design principles:\n\n* Custom `main` function\n* Dependency injection\n* Limited scope with unit testing.\n\nAlso:\n\n* Adding your functions to the generated `configure_swagger_*.go` seems to be a burden.\n* Lack of Interface that the service implements.\n* Complicated and custom http clients and runtime.\n\nThose are the changes that this contributor templates are providing:\n\n## Server\n\n### The new `restapi` package exposes interfaces\n\n* Those interfaces can be implemented by the developer and are the business logic of the service.\n* The implementation of those is extensible.\n* The implementation is separated from the generated code.\n\n### The `restapi` returns an `http.Handler`\n\nThe `restapi.Handler` (see [example](./example/restapi/configure_swagger_petstore.go)) function returns\na standard `http.Handler`\n\n* Given objects that implements the business logic, we can create a simple http handler.\n* This handler is a standard go http.Handler, so we can now use any other middleware, library, or framework\nthat supports it.\n* This handler is standard, so we understand it better.\n\n## Client\n\n* The new client package exposes interfaces, so functions in our code can receive those\n  interfaces which can be mocked for testing.\n* The new client has a config that gets an `*url.URL` to customize the endpoint.\n* The new client has a config that gets an `http.RoundTripper` to customize client with libraries, middleware or\n  frameworks that support the standard library's objects.\n\n# Example Walk-Through\n\nIn the [example package](https://github.com/Stratoscale/swagger/tree/master/example) you'll find generated code and usage of the pet-store\n[swagger file](./example/swagger.yaml).\n\n* The `restapi`, `models` and `client` are auto-generated by the stratoscale/swagger docker file.\n* The `internal` package was manually added and contains the server's business logic.\n* The `main.go` file is the entrypoint and contains initializations and dependency injections of the project.\n\n## Server\n\n### [restapi](https://github.com/Stratoscale/swagger/tree/master/example/restapi)\n\nThis package is autogenerated and contains the server routing and parameter parsing.\n\nThe modified version contains `restapi.PetAPI` and `restapi.StoreAPI` which were auto generated.\n\n```go\n// PetAPI\ntype PetAPI interface {\n\tPetCreate(ctx context.Context, params pet.PetCreateParams) middleware.Responder\n\tPetDelete(ctx context.Context, params pet.PetDeleteParams) middleware.Responder\n\tPetGet(ctx context.Context, params pet.PetGetParams) middleware.Responder\n\tPetList(ctx context.Context, params pet.PetListParams) middleware.Responder\n\tPetUpdate(ctx context.Context, params pet.PetUpdateParams) middleware.Responder\n}\n\n//go:generate mockery -name StoreAPI -inpkg\n\n// StoreAPI\ntype StoreAPI interface {\n\tInventoryGet(ctx context.Context, params store.InventoryGetParams) middleware.Responder\n\tOrderCreate(ctx context.Context, params store.OrderCreateParams) middleware.Responder\n\t// OrderDelete is For valid response try integer IDs with positive integer value. Negative or non-integer values will generate API errors\n\tOrderDelete(ctx context.Context, params store.OrderDeleteParams) middleware.Responder\n\t// OrderGet is For valid response try integer IDs with value >= 1 and <= 10. Other values will generated exceptions\n\tOrderGet(ctx context.Context, params store.OrderGetParams) middleware.Responder\n}\n```\n\nEach function matches an `operationId` in the swagger file and they are grouped according to\nthe operation `tags`.\n\nThere is also a `restapi.Config`:\n\n```go\n// Config is configuration for Handler\ntype Config struct {\n\tPetAPI\n\tStoreAPI\n\tLogger func(string, ...any)\n\t// InnerMiddleware is for the handler executors. These do not apply to the swagger.json document.\n\t// The middleware executes after routing but before authentication, binding and validation\n\tInnerMiddleware func(http.Handler) http.Handler\n}\n```\n\nThis config is auto generated and contains all the declared interfaces above.\nIt is used to initiate an http.Handler with the `Handler` function:\n\n```go\n// Handler returns an http.Handler given the handler configuration\n// It mounts all the business logic implementers in the right routing.\nfunc Handler(c Config) (http.Handler, error) {\n    ...\n```\n\nLet's look how we use this generated code to build our server.\n\n### [internal](https://github.com/Stratoscale/swagger/tree/master/example/internal)\n\nThe `internal` package is **not** auto generated and contains the business logic of our server.\nWe can see two structs that implement the `restapi.PetAPI` and `restapi.StoreAPI` interfaces,\nneeded to make our server work.\n\nWhen adding or removing functions from our REST API, we can just add or remove functions to those\nbusiness logic units. We can also create new logical units when they are added to our REST API.\n\n### [main.go](./example/main.go)\n\nThe main function is pretty straight forward. We initiate our business logic units.\nThen create a config for our rest API. We then create a standard `http.Handler` which we can\nupdate with middleware, test with `httptest`, or to use with other standard tools.\nThe last piece is to run the handler with `http.ListenAndServe` or to use it with an `http.Server` -\nit is all very customizable.\n\n```go\nfunc main() {\n\t// Initiate business logic implementers.\n\t// This is the main function, so here the implementers' dependencies can be\n\t// injected, such as database, parameters from environment variables, or different\n\t// clients for different APIs.\n\tp := internal.Pet{}\n\ts := internal.Store{}\n\n\t// Initiate the http handler, with the objects that are implementing the business logic.\n\th, err := restapi.Handler(restapi.Config{\n\t\tPetAPI:   &p,\n\t\tStoreAPI: &s,\n\t\tLogger:   log.Printf,\n\t})\n\tif err != nil {\n\t\tlog.Fatal(err)\n\t}\n\n\t// Run the standard http server\n\tlog.Fatal(http.ListenAndServe(\":8080\", h))\n}\n```\n\n## Client\n\nThe client code is in the [client package](https://github.com/Stratoscale/swagger/tree/master/example/client) and is autogenerated.\n\nTo create a new client we use the `client.Config` struct:\n\n```go\ntype Config struct {\n\t// URL is the base URL of the upstream server\n\tURL *url.URL\n\t// Transport is an inner transport for the client\n\tTransport http.RoundTripper\n}\n```\n\nThis enables us to use custom server endpoint or custom client middleware. Easily, with the\nstandard components, and with any library that accepts them.\n\nThe client is then generated with the New method:\n\n```go\n// New creates a new swagger petstore HTTP client.\nfunc New(c Config) *SwaggerPetstore { ... }\n```\n\nThis method returns an object that has two important fields:\n\n```go\ntype SwaggerPetstore {\n\t...\n\tPet       *pet.Client\n\tStore     *store.Client\n}\n```\n\nThose fields are objects, which implement interfaces declared in the [pet](./example/client/pet) and\n[store](./example/client/store) packages:\n\nFor example:\n\n```go\n// API is the interface of the pet client\ntype API interface {\n\t// PetCreate adds a new pet to the store\n\tPetCreate(ctx context.Context, params *PetCreateParams) (*PetCreateCreated, error)\n\t// PetDelete deletes a pet\n\tPetDelete(ctx context.Context, params *PetDeleteParams) (*PetDeleteNoContent, error)\n\t// PetGet gets pet by it s ID\n\tPetGet(ctx context.Context, params *PetGetParams) (*PetGetOK, error)\n\t// PetList lists pets\n\tPetList(ctx context.Context, params *PetListParams) (*PetListOK, error)\n\t// PetUpdate updates an existing pet\n\tPetUpdate(ctx context.Context, params *PetUpdateParams) (*PetUpdateCreated, error)\n}\n```\n\nThey are very similar to the server interfaces, and can be used by consumers of those APIs\n(instead of using the actual client or the `*Pet` struct)\n\n# Authentication\n\nAuthenticating and policy enforcement of the application is done in several stages, described below.\n\n## Define security in swagger.yaml\n\nAdd to the root of the swagger.yaml the security and security definitions sections.\n\n```yaml\nsecurityDefinitions:\n  token:\n    type: apiKey\n    in: header\n    name: Cookie\n\nsecurity:\n  - token: []\n```\n\nThe securityDefinitions section defines different security types that your application can handle.\nThe supported types by go-swagger are:\n* `apiKey` - token that should be able to be processed.\n* `oauth2` - token and scopes that should be processed. \n* and `basic` - user/password that should be processed.\n\nHere we defined an apiKey, that is passed through the Cookie header.\n\nThe `security` section defines the default security enforcement for the application. You can select\ndifferent securityDefinitions, as the keys, and apply \"scopes\" as the values. Those default definitions\ncan be overridden in each route by a section with the same name:\n\n```yaml\npaths:\n  /pets:\n    post:\n      [...]\n      security:\n        - token: [admin]\n```\n\nHere we have overridden the scope of the token in the POST /pets URL so that only admin can use this API.\n\nLet's see how we can use this functionality.\n\n## Writing Security Handlers\n\nOnce we created a security definition named \"token\", a function called \"AuthToken\" was added to the `restapi.Config`:\n\n```go\ntype Config struct {\n    ...\n\t// AuthToken Applies when the \"Cookie\" header is set\n\tAuthToken func(token string) (any, error)\n}\n```\n\nThis function gets the content of the Cookie header, and should return an `any` and `error`.\nThe `any` is the object that should represent the user that performed the request, it should\nbe nil to return an unauthorized 401 HTTP response. If the returned `error` is not nil, an HTTP 500,\ninternal server error will be returned.\n\nThe returned object, will be stored in the request context under the `restapi.AuthKey` key.\n\nThere is another function that we should know about, in the `restapi.Config` struct:\n\n```go\ntype Config struct {\n\t...\n\t// Authorizer is used to authorize a request after the Auth function was called using the \"Auth*\" functions\n\t// and the principal was stored in the context in the \"AuthKey\" context value.\n\tAuthorizer func(*http.Request) error\n}\n```\n\nThis one is a custom defined function that gets the request and can return an error.\nIf the returned error is not nil, and 403 HTTP error will be returned to the client - here the policy\nenforcement comes into play.\nThere are two things that this function should be aware of:\n\n1. The user - it can retrieve the user information from the context: `ctx.Value(restapi.AuthKey).(MyUserType)`.\n   Usually, a server will have a function for extracting this user information and returns a concrete\n   type which could be used by all the routes.\n2. The route - it can retrieve the route using the go-swagger function: `middleware.MatchedRouteFrom(*http.Request)`.\n   So no need to parse the URL and test the request method.\n   This route struct contains the route information. If for example, we want to check the scopes that were\n   defined for the current route in the swagger.yaml we can use the code below:\n   \n```go\nfor _, auth := range route.Authenticators {\n    for scopeName, scopeValues := range auth.Scopes {\n        for _, scopeValue := range scopeValues {\n            ...\n        }\n    }\n}\n```\n","tools/migrate_chart/Readme.md":"# Chart Migrating Tool\n\nHarbor supports two different ways to storage the chart data.\n\n   1. stored in Harbor registry storage directly via OCI API.\n   2. stored in Harbor hosted chartmuseum backend via chartmuseam's API\n\nThere is an performance issue in chartmuseam. For example, on my 2 core 8G memory test environment, to get 10000 charts information needs about 10s to return, In 50000 charts situation, It will cause a timeout error.\n\nAfter version 2.0, Harbor becomes to the OCI registry. So It can storage chart content directly without chartmuseum.\n\nThis tool used to migrate the legacy helm charts stored in the chartmuseum backend to Harbor OCI registry backend.\n\nOn test environment( 2 core 8G memory), using this tool to migrate 10000 charts needs about 2~3 hours\n\n## Usages\n\nCompile the chart with command\n\n``` sh\ndocker build -t goharbor/migrate-chart:0.1.0 .\n```\n\nMigrate charts run command below:\n\n``` sh\ndocker run -it --rm -v {{your_chart_data_location}}:/chart_storage -v {{harbor_ca_cert_location}}:/usr/local/share/ca-certificates/harbor_ca.crt  goharbor/migrate-chart:0.1.0 --hostname {{harbor_hostname}} --password {{harbor_admin_password}}\n```\n\n* `your_chart_data_location`: The location of your chart storage chart. By default, it's the `chart_storage` dir inside Harbor's `data_volumn`\n\n* `harbor_ca_cert_location`: If Harbor enabled HTTPS, you need to add the `ca_cert` for connecting Harbor\n\n* `harbor_hostname`: The hostname of Harbor\n\n* `harbor_admin_password`: The password of harbor admin user\n"},"items":[{"name":"Readme.md","path":"tools/migrate_chart/Readme.md","rawUrl":"https://raw.githubusercontent.com/goharbor/harbor/HEAD/tools/migrate_chart/Readme.md","title":"migrate_chart Documentation","category":"plugin-manifest","format":"markdown","content":"# Chart Migrating Tool\n\nHarbor supports two different ways to storage the chart data.\n\n   1. stored in Harbor registry storage directly via OCI API.\n   2. stored in Harbor hosted chartmuseum backend via chartmuseam's API\n\nThere is an performance issue in chartmuseam. For example, on my 2 core 8G memory test environment, to get 10000 charts information needs about 10s to return, In 50000 charts situation, It will cause a timeout error.\n\nAfter version 2.0, Harbor becomes to the OCI registry. So It can storage chart content directly without chartmuseum.\n\nThis tool used to migrate the legacy helm charts stored in the chartmuseum backend to Harbor OCI registry backend.\n\nOn test environment( 2 core 8G memory), using this tool to migrate 10000 charts needs about 2~3 hours\n\n## Usages\n\nCompile the chart with command\n\n``` sh\ndocker build -t goharbor/migrate-chart:0.1.0 .\n```\n\nMigrate charts run command below:\n\n``` sh\ndocker run -it --rm -v {{your_chart_data_location}}:/chart_storage -v {{harbor_ca_cert_location}}:/usr/local/share/ca-certificates/harbor_ca.crt  goharbor/migrate-chart:0.1.0 --hostname {{harbor_hostname}} --password {{harbor_admin_password}}\n```\n\n* `your_chart_data_location`: The location of your chart storage chart. By default, it's the `chart_storage` dir inside Harbor's `data_volumn`\n\n* `harbor_ca_cert_location`: If Harbor enabled HTTPS, you need to add the `ca_cert` for connecting Harbor\n\n* `harbor_hostname`: The hostname of Harbor\n\n* `harbor_admin_password`: The password of harbor admin user\n","isInternal":false,"tokens":380,"sizeBytes":1526},{"name":"README.md","path":"tools/swagger/templates/README.md","rawUrl":"https://raw.githubusercontent.com/goharbor/harbor/HEAD/tools/swagger/templates/README.md","title":"templates Documentation","category":"plugin-manifest","format":"markdown","content":"# swagger\n\nIn Stratoscale, we really like the idea of API-first services, and we also really like Go.\nWe saw the go-swagger library, and thought that most of it can really help us. Generating code from\nswagger files is a big problem with a lot of corner cases, and go-swagger is doing great job.\n\nThe one thing that we felt missing was customization of the server to run with our design principles:\n\n* Custom `main` function\n* Dependency injection\n* Limited scope with unit testing.\n\nAlso:\n\n* Adding your functions to the generated `configure_swagger_*.go` seems to be a burden.\n* Lack of Interface that the service implements.\n* Complicated and custom http clients and runtime.\n\nThose are the changes that this contributor templates are providing:\n\n## Server\n\n### The new `restapi` package exposes interfaces\n\n* Those interfaces can be implemented by the developer and are the business logic of the service.\n* The implementation of those is extensible.\n* The implementation is separated from the generated code.\n\n### The `restapi` returns an `http.Handler`\n\nThe `restapi.Handler` (see [example](./example/restapi/configure_swagger_petstore.go)) function returns\na standard `http.Handler`\n\n* Given objects that implements the business logic, we can create a simple http handler.\n* This handler is a standard go http.Handler, so we can now use any other middleware, library, or framework\nthat supports it.\n* This handler is standard, so we understand it better.\n\n## Client\n\n* The new client package exposes interfaces, so functions in our code can receive those\n  interfaces which can be mocked for testing.\n* The new client has a config that gets an `*url.URL` to customize the endpoint.\n* The new client has a config that gets an `http.RoundTripper` to customize client with libraries, middleware or\n  frameworks that support the standard library's objects.\n\n# Example Walk-Through\n\nIn the [example package](https://github.com/Stratoscale/swagger/tree/master/example) you'll find generated code and usage of the pet-store\n[swagger file](./example/swagger.yaml).\n\n* The `restapi`, `models` and `client` are auto-generated by the stratoscale/swagger docker file.\n* The `internal` package was manually added and contains the server's business logic.\n* The `main.go` file is the entrypoint and contains initializations and dependency injections of the project.\n\n## Server\n\n### [restapi](https://github.com/Stratoscale/swagger/tree/master/example/restapi)\n\nThis package is autogenerated and contains the server routing and parameter parsing.\n\nThe modified version contains `restapi.PetAPI` and `restapi.StoreAPI` which were auto generated.\n\n```go\n// PetAPI\ntype PetAPI interface {\n\tPetCreate(ctx context.Context, params pet.PetCreateParams) middleware.Responder\n\tPetDelete(ctx context.Context, params pet.PetDeleteParams) middleware.Responder\n\tPetGet(ctx context.Context, params pet.PetGetParams) middleware.Responder\n\tPetList(ctx context.Context, params pet.PetListParams) middleware.Responder\n\tPetUpdate(ctx context.Context, params pet.PetUpdateParams) middleware.Responder\n}\n\n//go:generate mockery -name StoreAPI -inpkg\n\n// StoreAPI\ntype StoreAPI interface {\n\tInventoryGet(ctx context.Context, params store.InventoryGetParams) middleware.Responder\n\tOrderCreate(ctx context.Context, params store.OrderCreateParams) middleware.Responder\n\t// OrderDelete is For valid response try integer IDs with positive integer value. Negative or non-integer values will generate API errors\n\tOrderDelete(ctx context.Context, params store.OrderDeleteParams) middleware.Responder\n\t// OrderGet is For valid response try integer IDs with value >= 1 and <= 10. Other values will generated exceptions\n\tOrderGet(ctx context.Context, params store.OrderGetParams) middleware.Responder\n}\n```\n\nEach function matches an `operationId` in the swagger file and they are grouped according to\nthe operation `tags`.\n\nThere is also a `restapi.Config`:\n\n```go\n// Config is configuration for Handler\ntype Config struct {\n\tPetAPI\n\tStoreAPI\n\tLogger func(string, ...any)\n\t// InnerMiddleware is for the handler executors. These do not apply to the swagger.json document.\n\t// The middleware executes after routing but before authentication, binding and validation\n\tInnerMiddleware func(http.Handler) http.Handler\n}\n```\n\nThis config is auto generated and contains all the declared interfaces above.\nIt is used to initiate an http.Handler with the `Handler` function:\n\n```go\n// Handler returns an http.Handler given the handler configuration\n// It mounts all the business logic implementers in the right routing.\nfunc Handler(c Config) (http.Handler, error) {\n    ...\n```\n\nLet's look how we use this generated code to build our server.\n\n### [internal](https://github.com/Stratoscale/swagger/tree/master/example/internal)\n\nThe `internal` package is **not** auto generated and contains the business logic of our server.\nWe can see two structs that implement the `restapi.PetAPI` and `restapi.StoreAPI` interfaces,\nneeded to make our server work.\n\nWhen adding or removing functions from our REST API, we can just add or remove functions to those\nbusiness logic units. We can also create new logical units when they are added to our REST API.\n\n### [main.go](./example/main.go)\n\nThe main function is pretty straight forward. We initiate our business logic units.\nThen create a config for our rest API. We then create a standard `http.Handler` which we can\nupdate with middleware, test with `httptest`, or to use with other standard tools.\nThe last piece is to run the handler with `http.ListenAndServe` or to use it with an `http.Server` -\nit is all very customizable.\n\n```go\nfunc main() {\n\t// Initiate business logic implementers.\n\t// This is the main function, so here the implementers' dependencies can be\n\t// injected, such as database, parameters from environment variables, or different\n\t// clients for different APIs.\n\tp := internal.Pet{}\n\ts := internal.Store{}\n\n\t// Initiate the http handler, with the objects that are implementing the business logic.\n\th, err := restapi.Handler(restapi.Config{\n\t\tPetAPI:   &p,\n\t\tStoreAPI: &s,\n\t\tLogger:   log.Printf,\n\t})\n\tif err != nil {\n\t\tlog.Fatal(err)\n\t}\n\n\t// Run the standard http server\n\tlog.Fatal(http.ListenAndServe(\":8080\", h))\n}\n```\n\n## Client\n\nThe client code is in the [client package](https://github.com/Stratoscale/swagger/tree/master/example/client) and is autogenerated.\n\nTo create a new client we use the `client.Config` struct:\n\n```go\ntype Config struct {\n\t// URL is the base URL of the upstream server\n\tURL *url.URL\n\t// Transport is an inner transport for the client\n\tTransport http.RoundTripper\n}\n```\n\nThis enables us to use custom server endpoint or custom client middleware. Easily, with the\nstandard components, and with any library that accepts them.\n\nThe client is then generated with the New method:\n\n```go\n// New creates a new swagger petstore HTTP client.\nfunc New(c Config) *SwaggerPetstore { ... }\n```\n\nThis method returns an object that has two important fields:\n\n```go\ntype SwaggerPetstore {\n\t...\n\tPet       *pet.Client\n\tStore     *store.Client\n}\n```\n\nThose fields are objects, which implement interfaces declared in the [pet](./example/client/pet) and\n[store](./example/client/store) packages:\n\nFor example:\n\n```go\n// API is the interface of the pet client\ntype API interface {\n\t// PetCreate adds a new pet to the store\n\tPetCreate(ctx context.Context, params *PetCreateParams) (*PetCreateCreated, error)\n\t// PetDelete deletes a pet\n\tPetDelete(ctx context.Context, params *PetDeleteParams) (*PetDeleteNoContent, error)\n\t// PetGet gets pet by it s ID\n\tPetGet(ctx context.Context, params *PetGetParams) (*PetGetOK, error)\n\t// PetList lists pets\n\tPetList(ctx context.Context, params *PetListParams) (*PetListOK, error)\n\t// PetUpdate updates an existing pet\n\tPetUpdate(ctx context.Context, params *PetUpdateParams) (*PetUpdateCreated, error)\n}\n```\n\nThey are very similar to the server interfaces, and can be used by consumers of those APIs\n(instead of using the actual client or the `*Pet` struct)\n\n# Authentication\n\nAuthenticating and policy enforcement of the application is done in several stages, described below.\n\n## Define security in swagger.yaml\n\nAdd to the root of the swagger.yaml the security and security definitions sections.\n\n```yaml\nsecurityDefinitions:\n  token:\n    type: apiKey\n    in: header\n    name: Cookie\n\nsecurity:\n  - token: []\n```\n\nThe securityDefinitions section defines different security types that your application can handle.\nThe supported types by go-swagger are:\n* `apiKey` - token that should be able to be processed.\n* `oauth2` - token and scopes that should be processed. \n* and `basic` - user/password that should be processed.\n\nHere we defined an apiKey, that is passed through the Cookie header.\n\nThe `security` section defines the default security enforcement for the application. You can select\ndifferent securityDefinitions, as the keys, and apply \"scopes\" as the values. Those default definitions\ncan be overridden in each route by a section with the same name:\n\n```yaml\npaths:\n  /pets:\n    post:\n      [...]\n      security:\n        - token: [admin]\n```\n\nHere we have overridden the scope of the token in the POST /pets URL so that only admin can use this API.\n\nLet's see how we can use this functionality.\n\n## Writing Security Handlers\n\nOnce we created a security definition named \"token\", a function called \"AuthToken\" was added to the `restapi.Config`:\n\n```go\ntype Config struct {\n    ...\n\t// AuthToken Applies when the \"Cookie\" header is set\n\tAuthToken func(token string) (any, error)\n}\n```\n\nThis function gets the content of the Cookie header, and should return an `any` and `error`.\nThe `any` is the object that should represent the user that performed the request, it should\nbe nil to return an unauthorized 401 HTTP response. If the returned `error` is not nil, an HTTP 500,\ninternal server error will be returned.\n\nThe returned object, will be stored in the request context under the `restapi.AuthKey` key.\n\nThere is another function that we should know about, in the `restapi.Config` struct:\n\n```go\ntype Config struct {\n\t...\n\t// Authorizer is used to authorize a request after the Auth function was called using the \"Auth*\" functions\n\t// and the principal was stored in the context in the \"AuthKey\" context value.\n\tAuthorizer func(*http.Request) error\n}\n```\n\nThis one is a custom defined function that gets the request and can return an error.\nIf the returned error is not nil, and 403 HTTP error will be returned to the client - here the policy\nenforcement comes into play.\nThere are two things that this function should be aware of:\n\n1. The user - it can retrieve the user information from the context: `ctx.Value(restapi.AuthKey).(MyUserType)`.\n   Usually, a server will have a function for extracting this user information and returns a concrete\n   type which could be used by all the routes.\n2. The route - it can retrieve the route using the go-swagger function: `middleware.MatchedRouteFrom(*http.Request)`.\n   So no need to parse the URL and test the request method.\n   This route struct contains the route information. If for example, we want to check the scopes that were\n   defined for the current route in the swagger.yaml we can use the code below:\n   \n```go\nfor _, auth := range route.Authenticators {\n    for scopeName, scopeValues := range auth.Scopes {\n        for _, scopeValue := range scopeValues {\n            ...\n        }\n    }\n}\n```\n","isInternal":false,"tokens":2566,"sizeBytes":11427}],"systemPromptSnippet":"<yakaai_skills repo=\"goharbor/harbor\">\n<!-- File: tools/migrate_chart/Readme.md (Tokens: ~380 | Category: plugin-manifest) -->\n# Chart Migrating Tool\n\nHarbor supports two different ways to storage the chart data.\n\n   1. stored in Harbor registry storage directly via OCI API.\n   2. stored in Harbor hosted chartmuseum backend via chartmuseam's API\n\nThere is an performance issue in chartmuseam. For example, on my 2 core 8G memory test environment, to get 10000 charts information needs about 10s to return, In 50000 charts situation, It will cause a timeout error.\n\nAfter version 2.0, Harbor becomes to the OCI registry. So It can storage chart content directly without chartmuseum.\n\nThis tool used to migrate the legacy helm charts stored in the chartmuseum backend to Harbor OCI registry backend.\n\nOn test environment( 2 core 8G memory), using this tool to migrate 10000 charts needs about 2~3 hours\n\n## Usages\n\nCompile the chart with command\n\n``` sh\ndocker build -t goharbor/migrate-chart:0.1.0 .\n```\n\nMigrate charts run command below:\n\n``` sh\ndocker run -it --rm -v {{your_chart_data_location}}:/chart_storage -v {{harbor_ca_cert_location}}:/usr/local/share/ca-certificates/harbor_ca.crt  goharbor/migrate-chart:0.1.0 --hostname {{harbor_hostname}} --password {{harbor_admin_password}}\n```\n\n* `your_chart_data_location`: The location of your chart storage chart. By default, it's the `chart_storage` dir inside Harbor's `data_volumn`\n\n* `harbor_ca_cert_location`: If Harbor enabled HTTPS, you need to add the `ca_cert` for connecting Harbor\n\n* `harbor_hostname`: The hostname of Harbor\n\n* `harbor_admin_password`: The password of harbor admin user\n\n<!-- File: tools/swagger/templates/README.md (Tokens: ~2566 | Category: plugin-manifest) -->\n# swagger\n\nIn Stratoscale, we really like the idea of API-first services, and we also really like Go.\nWe saw the go-swagger library, and thought that most of it can really help us. Generating code from\nswagger files is a big problem with a lot of corner cases, and go-swagger is doing great job.\n\nThe one thing that we felt missing was customization of the server to run with our design principles:\n\n* Custom `main` function\n* Dependency injection\n* Limited scope with unit testing.\n\nAlso:\n\n* Adding your functions to the generated `configure_swagger_*.go` seems to be a burden.\n* Lack of Interface that the service implements.\n* Complicated and custom http clients and runtime.\n\nThose are the changes that this contributor templates are providing:\n\n## Server\n\n### The new `restapi` package exposes interfaces\n\n* Those interfaces can be implemented by the developer and are the business logic of the service.\n* The implementation of those is extensible.\n* The implementation is separated from the generated code.\n\n### The `restapi` returns an `http.Handler`\n\nThe `restapi.Handler` (see [example](./example/restapi/configure_swagger_petstore.go)) function returns\na standard `http.Handler`\n\n* Given objects that implements the business logic, we can create a simple http handler.\n* This handler is a standard go http.Handler, so we can now use any other middleware, library, or framework\nthat supports it.\n* This handler is standard, so we understand it better.\n\n## Client\n\n* The new client package exposes interfaces, so functions in our code can receive those\n  interfaces which can be mocked for testing.\n* The new client has a config that gets an `*url.URL` to customize the endpoint.\n* The new client has a config that gets an `http.RoundTripper` to customize client with libraries, middleware or\n  frameworks that support the standard library's objects.\n\n# Example Walk-Through\n\nIn the [example package](https://github.com/Stratoscale/swagger/tree/master/example) you'll find generated code and usage of the pet-store\n[swagger file](./example/swagger.yaml).\n\n* The `restapi`, `models` and `client` are auto-generated by the stratoscale/swagger docker file.\n* The `internal` package was manually added and contains the server's business logic.\n* The `main.go` file is the entrypoint and contains initializations and dependency injections of the project.\n\n## Server\n\n### [restapi](https://github.com/Stratoscale/swagger/tree/master/example/restapi)\n\nThis package is autogenerated and contains the server routing and parameter parsing.\n\nThe modified version contains `restapi.PetAPI` and `restapi.StoreAPI` which were auto generated.\n\n```go\n// PetAPI\ntype PetAPI interface {\n\tPetCreate(ctx context.Context, params pet.PetCreateParams) middleware.Responder\n\tPetDelete(ctx context.Context, params pet.PetDeleteParams) middleware.Responder\n\tPetGet(ctx context.Context, params pet.PetGetParams) middleware.Responder\n\tPetList(ctx context.Context, params pet.PetListParams) middleware.Responder\n\tPetUpdate(ctx context.Context, params pet.PetUpdateParams) middleware.Responder\n}\n\n//go:generate mockery -name StoreAPI -inpkg\n\n// StoreAPI\ntype StoreAPI interface {\n\tInventoryGet(ctx context.Context, params store.InventoryGetParams) middleware.Responder\n\tOrderCreate(ctx context.Context, params store.OrderCreateParams) middleware.Responder\n\t// OrderDelete is For valid response try integer IDs with positive integer value. Negative or non-integer values will generate API errors\n\tOrderDelete(ctx context.Context, params store.OrderDeleteParams) middleware.Responder\n\t// OrderGet is For valid response try integer IDs with value >= 1 and <= 10. Other values will generated exceptions\n\tOrderGet(ctx context.Context, params store.OrderGetParams) middleware.Responder\n}\n```\n\nEach function matches an `operationId` in the swagger file and they are grouped according to\nthe operation `tags`.\n\nThere is also a `restapi.Config`:\n\n```go\n// Config is configuration for Handler\ntype Config struct {\n\tPetAPI\n\tStoreAPI\n\tLogger func(string, ...any)\n\t// InnerMiddleware is for the handler executors. These do not apply to the swagger.json document.\n\t// The middleware executes after routing but before authentication, binding and validation\n\tInnerMiddleware func(http.Handler) http.Handler\n}\n```\n\nThis config is auto generated and contains all the declared interfaces above.\nIt is used to initiate an http.Handler with the `Handler` function:\n\n```go\n// Handler returns an http.Handler given the handler configuration\n// It mounts all the business logic implementers in the right routing.\nfunc Handler(c Config) (http.Handler, error) {\n    ...\n```\n\nLet's look how we use this generated code to build our server.\n\n### [internal](https://github.com/Stratoscale/swagger/tree/master/example/internal)\n\nThe `internal` package is **not** auto generated and contains the business logic of our server.\nWe can see two structs that implement the `restapi.PetAPI` and `restapi.StoreAPI` interfaces,\nneeded to make our server work.\n\nWhen adding or removing functions from our REST API, we can just add or remove functions to those\nbusiness logic units. We can also create new logical units when they are added to our REST API.\n\n### [main.go](./example/main.go)\n\nThe main function is pretty straight forward. We initiate our business logic units.\nThen create a config for our rest API. We then create a standard `http.Handler` which we can\nupdate with middleware, test with `httptest`, or to use with other standard tools.\nThe last piece is to run the handler with `http.ListenAndServe` or to use it with an `http.Server` -\nit is all very customizable.\n\n```go\nfunc main() {\n\t// Initiate business logic implementers.\n\t// This is the main function, so here the implementers' dependencies can be\n\t// injected, such as database, parameters from environment variables, or different\n\t// clients for different APIs.\n\tp := internal.Pet{}\n\ts := internal.Store{}\n\n\t// Initiate the http handler, with the objects that are implementing the business logic.\n\th, err := restapi.Handler(restapi.Config{\n\t\tPetAPI:   &p,\n\t\tStoreAPI: &s,\n\t\tLogger:   log.Printf,\n\t})\n\tif err != nil {\n\t\tlog.Fatal(err)\n\t}\n\n\t// Run the standard http server\n\tlog.Fatal(http.ListenAndServe(\":8080\", h))\n}\n```\n\n## Client\n\nThe client code is in the [client package](https://github.com/Stratoscale/swagger/tree/master/example/client) and is autogenerated.\n\nTo create a new client we use the `client.Config` struct:\n\n```go\ntype Config struct {\n\t// URL is the base URL of the upstream server\n\tURL *url.URL\n\t// Transport is an inner transport for the client\n\tTransport http.RoundTripper\n}\n```\n\nThis enables us to use custom server endpoint or custom client middleware. Easily, with the\nstandard components, and with any library that accepts them.\n\nThe client is then generated with the New method:\n\n```go\n// New creates a new swagger petstore HTTP client.\nfunc New(c Config) *SwaggerPetstore { ... }\n```\n\nThis method returns an object that has two important fields:\n\n```go\ntype SwaggerPetstore {\n\t...\n\tPet       *pet.Client\n\tStore     *store.Client\n}\n```\n\nThose fields are objects, which implement interfaces declared in the [pet](./example/client/pet) and\n[store](./example/client/store) packages:\n\nFor example:\n\n```go\n// API is the interface of the pet client\ntype API interface {\n\t// PetCreate adds a new pet to the store\n\tPetCreate(ctx context.Context, params *PetCreateParams) (*PetCreateCreated, error)\n\t// PetDelete deletes a pet\n\tPetDelete(ctx context.Context, params *PetDeleteParams) (*PetDeleteNoContent, error)\n\t// PetGet gets pet by it s ID\n\tPetGet(ctx context.Context, params *PetGetParams) (*PetGetOK, error)\n\t// PetList lists pets\n\tPetList(ctx context.Context, params *PetListParams) (*PetListOK, error)\n\t// PetUpdate updates an existing pet\n\tPetUpdate(ctx context.Context, params *PetUpdateParams) (*PetUpdateCreated, error)\n}\n```\n\nThey are very similar to the server interfaces, and can be used by consumers of those APIs\n(instead of using the actual client or the `*Pet` struct)\n\n# Authentication\n\nAuthenticating and policy enforcement of the application is done in several stages, described below.\n\n## Define security in swagger.yaml\n\nAdd to the root of the swagger.yaml the security and security definitions sections.\n\n```yaml\nsecurityDefinitions:\n  token:\n    type: apiKey\n    in: header\n    name: Cookie\n\nsecurity:\n  - token: []\n```\n\nThe securityDefinitions section defines different security types that your application can handle.\nThe supported types by go-swagger are:\n* `apiKey` - token that should be able to be processed.\n* `oauth2` - token and scopes that should be processed. \n* and `basic` - user/password that should be processed.\n\nHere we defined an apiKey, that is passed through the Cookie header.\n\nThe `security` section defines the default security enforcement for the application. You can select\ndifferent securityDefinitions, as the keys, and apply \"scopes\" as the values. Those default definitions\ncan be overridden in each route by a section with the same name:\n\n```yaml\npaths:\n  /pets:\n    post:\n      [...]\n      security:\n        - token: [admin]\n```\n\nHere we have overridden the scope of the token in the POST /pets URL so that only admin can use this API.\n\nLet's see how we can use this functionality.\n\n## Writing Security Handlers\n\nOnce we created a security definition named \"token\", a function called \"AuthToken\" was added to the `restapi.Config`:\n\n```go\ntype Config struct {\n    ...\n\t// AuthToken Applies when the \"Cookie\" header is set\n\tAuthToken func(token string) (any, error)\n}\n```\n\nThis function gets the content of the Cookie header, and should return an `any` and `error`.\nThe `any` is the object that should represent the user that performed the request, it should\nbe nil to return an unauthorized 401 HTTP response. If the returned `error` is not nil, an HTTP 500,\ninternal server error will be returned.\n\nThe returned object, will be stored in the request context under the `restapi.AuthKey` key.\n\nThere is another function that we should know about, in the `restapi.Config` struct:\n\n```go\ntype Config struct {\n\t...\n\t// Authorizer is used to authorize a request after the Auth function was called using the \"Auth*\" functions\n\t// and the principal was stored in the context in the \"AuthKey\" context value.\n\tAuthorizer func(*http.Request) error\n}\n```\n\nThis one is a custom defined function that gets the request and can return an error.\nIf the returned error is not nil, and 403 HTTP error will be returned to the client - here the policy\nenforcement comes into play.\nThere are two things that this function should be aware of:\n\n1. The user - it can retrieve the user information from the context: `ctx.Value(restapi.AuthKey).(MyUserType)`.\n   Usually, a server will have a function for extracting this user information and returns a concrete\n   type which could be used by all the routes.\n2. The route - it can retrieve the route using the go-swagger function: `middleware.MatchedRouteFrom(*http.Request)`.\n   So no need to parse the URL and test the request method.\n   This route struct contains the route information. If for example, we want to check the scopes that were\n   defined for the current route in the swagger.yaml we can use the code below:\n   \n```go\nfor _, auth := range route.Authenticators {\n    for scopeName, scopeValues := range auth.Scopes {\n        for _, scopeValue := range scopeValues {\n            ...\n        }\n    }\n}\n```\n</yakaai_skills>"}