Skip to content

Commit 3832427

Browse files
Add V2 endpoints for Foxx Service (#698)
* Foxx: Add GetInstalledFoxxService endpoint to fetch installed Foxx services * Foxx: Add endpoint to fetch detailed information about a specific Foxx service * Foxx: few test scenarios added * Done response code and testcase chages for install and uninstall fox service * Add replace foxx service endpoint * Add upgrade foxx service endpoint * Add endpoint to fetch configuration for a specified foxx service mount * Comments added * Add endpoint to upload configuration options for a specific foxx service * Foxx: Add endpoint for replace foxx service * Foxx: Add endpoint to fetch foxx service dependencies * Foxx: Add endpoint to update foxx service dependencies * Foxx: Add endpoint to replace foxx service dependencies * Foxx: Add endpoints related to fox service scripts * Foxx: Add endpoints for RunFoxServiceScripts Enable and Disable development modes * Foxx: Add endpoint to get fox service readme content * change test case zip file name * Foxx: Add endpoint for swagger fox service * Foxx: Add endpoint to commit local service state * Foxx: Add endpoint to download specific service * changed the zip file path * reverted the zip file path * changes in config * changes in config file * changes in config file * reverted workflows in config file and added resources-path * reverted workflows in config file * trying to from test file that check temp resources is there or not * In config file moved download-demo-data above the run-integration-tests * reverted config changes * Added echo in config file * identation fixed * code changes in config * code changes in config * tag added in changelog * Update v2/tests/foxx_test.go Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com> * ci: trigger CircleCI build * Addressed copilot commets * Addressed copilot comment * Addressed copilot comment for uninstall * Addressed copilot comment for uninstall --------- Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
1 parent 3e8113c commit 3832427

File tree

5 files changed

+1122
-50
lines changed

5 files changed

+1122
-50
lines changed

.circleci/config.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -157,4 +157,4 @@ workflows:
157157
cron: 0 6 * * 1
158158
filters:
159159
branches:
160-
only: master
160+
only: master

v2/CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
- Add missing endpoints from collections to v2
66
- Add missing endpoints from query to v2
77
- Add SSO auth token implementation
8+
- Add missing endpoints from foxx to v2
89

910
## [2.1.3](https://github.com/arangodb/go-driver/tree/v2.1.3) (2025-02-21)
1011
- Switch to Go 1.22.11

v2/arangodb/client_foxx.go

Lines changed: 242 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -33,12 +33,88 @@ type ClientFoxx interface {
3333

3434
type ClientFoxxService interface {
3535
// InstallFoxxService installs a new service at a given mount path.
36-
InstallFoxxService(ctx context.Context, dbName string, zipFile string, options *FoxxCreateOptions) error
36+
InstallFoxxService(ctx context.Context, dbName string, zipFile string, options *FoxxDeploymentOptions) error
3737
// UninstallFoxxService uninstalls service at a given mount path.
3838
UninstallFoxxService(ctx context.Context, dbName string, options *FoxxDeleteOptions) error
39+
// ListInstalledFoxxServices retrieves the list of Foxx services installed in the specified database.
40+
// If excludeSystem is true, system services (like _admin/aardvark) will be excluded from the result,
41+
// returning only custom-installed Foxx services.
42+
ListInstalledFoxxServices(ctx context.Context, dbName string, excludeSystem *bool) ([]FoxxServiceListItem, error)
43+
// GetInstalledFoxxService retrieves detailed information about a specific Foxx service
44+
// installed in the specified database.
45+
// The service is identified by its mount path, which must be provided and non-empty.
46+
// If the mount path is missing or empty, a RequiredFieldError is returned.
47+
// The returned FoxxServiceObject contains the full metadata and configuration details
48+
// for the specified service.
49+
GetInstalledFoxxService(ctx context.Context, dbName string, mount *string) (FoxxServiceObject, error)
50+
// ReplaceFoxxService removes the service at the given mount path from the database and file system
51+
// and installs the given new service at the same mount path.
52+
ReplaceFoxxService(ctx context.Context, dbName string, zipFile string, opts *FoxxDeploymentOptions) error
53+
// UpgradeFoxxService installs the given new service on top of the service currently installed
54+
// at the specified mount path, retaining the existing service’s configuration and dependencies.
55+
// This should be used only when upgrading to a newer or equivalent version of the same service.
56+
UpgradeFoxxService(ctx context.Context, dbName string, zipFile string, opts *FoxxDeploymentOptions) error
57+
// GetFoxxServiceConfiguration retrieves the configuration values for the Foxx service
58+
// mounted at the specified path in the given database.
59+
// The mount parameter must not be nil or empty.
60+
// Returns a map containing the current configuration key-value pairs.
61+
GetFoxxServiceConfiguration(ctx context.Context, dbName string, mount *string) (map[string]interface{}, error)
62+
// UpdateFoxxServiceConfiguration updates the configuration of a specific Foxx service.
63+
// If the Foxx service does not allow a particular configuration key, it will appear
64+
// in the response warnings.
65+
// The caller is responsible for validating allowed keys before calling this method.
66+
UpdateFoxxServiceConfiguration(ctx context.Context, dbName string, mount *string, opt map[string]interface{}) (map[string]interface{}, error)
67+
// ReplaceFoxxServiceConfiguration replaces the given Foxx service's dependencies entirely.
68+
// If the Foxx service does not allow a particular configuration key, it will appear
69+
// in the response warnings.
70+
// The caller is responsible for validating allowed keys before calling this method.
71+
ReplaceFoxxServiceConfiguration(ctx context.Context, dbName string, mount *string, opt map[string]interface{}) (map[string]interface{}, error)
72+
73+
// GetFoxxServiceDependencies retrieves the configured dependencies for a specific Foxx service.
74+
// Returns:
75+
// A map where each key is a dependency name and the value is an object containing:
76+
// * title: Human-readable title of the dependency
77+
// * mount: Current mount path of the dependency service (if set)
78+
// An error if the request fails or the mount is missing.
79+
GetFoxxServiceDependencies(ctx context.Context, dbName string, mount *string) (map[string]interface{}, error)
80+
// UpdateFoxxServiceDependencies updates the configured dependencies of a specific Foxx service.
81+
// If the Foxx service does not allow a particular dependency key, it will appear
82+
// in the "warnings" field of the response.
83+
// The caller is responsible for ensuring that only allowed dependency keys are provided.
84+
UpdateFoxxServiceDependencies(ctx context.Context, dbName string, mount *string, opt map[string]interface{}) (map[string]interface{}, error)
85+
// ReplaceFoxxServiceDependencies replaces the given Foxx service's dependencies entirely.
86+
// If the Foxx service does not allow a particular dependency key, it will appear
87+
// in the "warnings" field of the response.
88+
// The caller is responsible for validating allowed keys before calling this method.
89+
ReplaceFoxxServiceDependencies(ctx context.Context, dbName string, mount *string, opt map[string]interface{}) (map[string]interface{}, error)
90+
// GetFoxxServiceScripts retrieves the scripts associated with a specific Foxx service.
91+
GetFoxxServiceScripts(ctx context.Context, dbName string, mount *string) (map[string]interface{}, error)
92+
// RunFoxxServiceScript executes a specific script associated with a Foxx service.
93+
RunFoxxServiceScript(ctx context.Context, dbName string, name string, mount *string, body map[string]interface{}) (map[string]interface{}, error)
94+
// RunFoxxServiceTests executes the test suite of a specific Foxx service
95+
// deployed in an ArangoDB database.
96+
RunFoxxServiceTests(ctx context.Context, dbName string, opt FoxxTestOptions) (map[string]interface{}, error)
97+
// EnableDevelopmentMode enables the development mode for a specific Foxx service.
98+
// Development mode causes the Foxx service to be reloaded from the filesystem and its setup
99+
// script (if present) to be re-executed every time the service handles a request.
100+
EnableDevelopmentMode(ctx context.Context, dbName string, mount *string) (map[string]interface{}, error)
101+
// DisableDevelopmentMode disables the development mode for a specific Foxx service.
102+
DisableDevelopmentMode(ctx context.Context, dbName string, mount *string) (map[string]interface{}, error)
103+
// GetFoxxServiceReadme retrieves the README file for a specific Foxx service.
104+
GetFoxxServiceReadme(ctx context.Context, dbName string, mount *string) ([]byte, error)
105+
// GetFoxxServiceSwagger retrieves the Swagger specification
106+
// for a specific Foxx service mounted in the given database.
107+
GetFoxxServiceSwagger(ctx context.Context, dbName string, mount *string) (SwaggerResponse, error)
108+
// CommitFoxxService commits the local Foxx service state of the Coordinator
109+
// to the database. This can resolve service conflicts between Coordinators.
110+
CommitFoxxService(ctx context.Context, dbName string, replace *bool) error
111+
// DownloadFoxxServiceBundle downloads a zip bundle of the Foxx service directory
112+
// from the specified database and mount point.
113+
// Note: The response is the raw zip data (binary).
114+
DownloadFoxxServiceBundle(ctx context.Context, dbName string, mount *string) ([]byte, error)
39115
}
40116

41-
type FoxxCreateOptions struct {
117+
type FoxxDeploymentOptions struct {
42118
Mount *string
43119
}
44120

@@ -48,22 +124,24 @@ type FoxxDeleteOptions struct {
48124
}
49125

50126
// ImportDocumentRequest holds Query parameters for /import.
51-
type InstallFoxxServiceRequest struct {
52-
FoxxCreateOptions `json:",inline"`
127+
type DeployFoxxServiceRequest struct {
128+
FoxxDeploymentOptions `json:",inline"`
53129
}
54130

55131
type UninstallFoxxServiceRequest struct {
56132
FoxxDeleteOptions `json:",inline"`
57133
}
58134

59-
func (c *InstallFoxxServiceRequest) modifyRequest(r connection.Request) error {
135+
func (c *DeployFoxxServiceRequest) modifyRequest(r connection.Request) error {
60136
if c == nil {
61137
return nil
62138
}
63139

64140
r.AddHeader(connection.ContentType, "application/zip")
65-
r.AddQuery("mount", *c.Mount)
66-
141+
if c.Mount != nil && *c.Mount != "" {
142+
mount := *c.Mount
143+
r.AddQuery("mount", mount)
144+
}
67145
return nil
68146
}
69147

@@ -72,8 +150,163 @@ func (c *UninstallFoxxServiceRequest) modifyRequest(r connection.Request) error
72150
return nil
73151
}
74152

75-
r.AddQuery("mount", *c.Mount)
76-
r.AddQuery("teardown", strconv.FormatBool(*c.Teardown))
153+
if c.Mount != nil && *c.Mount != "" {
154+
mount := *c.Mount
155+
r.AddQuery("mount", mount)
156+
}
157+
158+
if c.Teardown != nil {
159+
r.AddQuery("teardown", strconv.FormatBool(*c.Teardown))
160+
}
161+
77162
return nil
163+
}
164+
165+
type CommonFoxxServiceFields struct {
166+
// Mount is the mount path of the Foxx service in the database (e.g., "/my-service").
167+
// This determines the URL path at which the service can be accessed.
168+
Mount *string `json:"mount"`
169+
170+
// Development indicates whether the service is in development mode.
171+
// When true, the service is not cached and changes are applied immediately.
172+
Development *bool `json:"development"`
173+
174+
// Legacy indicates whether the service uses a legacy format or API.
175+
// This may be used for backward compatibility checks.
176+
Legacy *bool `json:"legacy"`
177+
// Name is the name of the Foxx service (optional).
178+
// This may be defined in the service manifest (manifest.json).
179+
Name *string `json:"name,omitempty"`
180+
181+
// Version is the version of the Foxx service (optional).
182+
// This is useful for managing service upgrades or deployments.
183+
Version *string `json:"version,omitempty"`
184+
}
185+
186+
// FoxxServiceListItem represents a single Foxx service installed in an ArangoDB database.
187+
type FoxxServiceListItem struct {
188+
CommonFoxxServiceFields
189+
// Provides lists the capabilities or interfaces the service provides.
190+
// This is a flexible map that may contain metadata like API contracts or service roles.
191+
Provides map[string]interface{} `json:"provides"`
192+
}
193+
194+
// Repository describes the version control repository for the Foxx service.
195+
type Repository struct {
196+
// Type is the type of repository (e.g., "git").
197+
Type *string `json:"type,omitempty"`
198+
199+
// URL is the link to the repository.
200+
URL *string `json:"url,omitempty"`
201+
}
202+
203+
// Contributor represents a person who contributed to the Foxx service.
204+
type Contributor struct {
205+
// Name is the contributor's name.
206+
Name *string `json:"name,omitempty"`
207+
208+
// Email is the contributor's contact email.
209+
Email *string `json:"email,omitempty"`
210+
}
211+
212+
// Engines specifies the ArangoDB engine requirements for the Foxx service.
213+
type Engines struct {
214+
// Arangodb specifies the required ArangoDB version range (semver format).
215+
Arangodb *string `json:"arangodb,omitempty"`
216+
}
217+
218+
// Manifest represents the normalized manifest.json of the Foxx service.
219+
type Manifest struct {
220+
// Schema is the JSON schema URL for the manifest structure.
221+
Schema *string `json:"$schema,omitempty"`
222+
223+
// Name is the name of the Foxx service.
224+
Name *string `json:"name,omitempty"`
225+
226+
// Version is the service's semantic version.
227+
Version *string `json:"version,omitempty"`
228+
229+
// License is the license identifier (e.g., "Apache-2.0").
230+
License *string `json:"license,omitempty"`
231+
232+
// Repository contains details about the service's source repository.
233+
Repository *Repository `json:"repository,omitempty"`
234+
235+
// Author is the main author of the service.
236+
Author *string `json:"author,omitempty"`
237+
238+
// Contributors is a list of people who contributed to the service.
239+
Contributors []*Contributor `json:"contributors,omitempty"`
240+
241+
// Description provides a human-readable explanation of the service.
242+
Description *string `json:"description,omitempty"`
243+
244+
// Engines specifies the engine requirements for running the service.
245+
Engines *Engines `json:"engines,omitempty"`
246+
247+
// DefaultDocument specifies the default document to serve (e.g., "index.html").
248+
DefaultDocument *string `json:"defaultDocument,omitempty"`
249+
250+
// Main specifies the main entry point JavaScript file of the service.
251+
Main *string `json:"main,omitempty"`
252+
253+
// Configuration contains service-specific configuration options.
254+
Configuration map[string]interface{} `json:"configuration,omitempty"`
255+
256+
// Dependencies defines other services or packages this service depends on.
257+
Dependencies map[string]interface{} `json:"dependencies,omitempty"`
258+
259+
// Files maps URL paths to static files or directories included in the service.
260+
Files map[string]interface{} `json:"files,omitempty"`
261+
262+
// Scripts contains script definitions for service lifecycle hooks or tasks.
263+
Scripts map[string]interface{} `json:"scripts,omitempty"`
264+
}
265+
266+
// FoxxServiceObject is the top-level response object for a Foxx service details request.
267+
type FoxxServiceObject struct {
268+
// Common fields for all Foxx services.
269+
CommonFoxxServiceFields
270+
271+
// Path is the local filesystem path where the service is installed.
272+
Path *string `json:"path,omitempty"`
273+
274+
// Manifest contains the normalized manifest.json of the service.
275+
Manifest *Manifest `json:"manifest,omitempty"`
276+
277+
// Options contains optional runtime options defined for the service.
278+
Options map[string]interface{} `json:"options,omitempty"`
279+
}
280+
281+
type FoxxTestOptions struct {
282+
FoxxDeploymentOptions
283+
Reporter *string `json:"reporter,omitempty"`
284+
Idiomatic *bool `json:"idiomatic,omitempty"`
285+
Filter *string `json:"filter,omitempty"`
286+
}
287+
288+
// SwaggerInfo contains general metadata about the API, typically displayed
289+
// in tools like Swagger UI.
290+
type SwaggerInfo struct {
291+
// Title is the title of the API.
292+
Title *string `json:"title,omitempty"`
293+
// Description provides a short description of the API.
294+
Description *string `json:"description,omitempty"`
295+
// Version specifies the version of the API.
296+
Version *string `json:"version,omitempty"`
297+
// License provides licensing information for the API.
298+
License map[string]interface{} `json:"license,omitempty"`
299+
}
78300

301+
// SwaggerResponse represents the root object of a Swagger (OpenAPI 2.0) specification.
302+
// It contains metadata, versioning information, available API paths, and additional details.
303+
type SwaggerResponse struct {
304+
// Swagger specifies the Swagger specification version (e.g., "2.0").
305+
Swagger *string `json:"swagger,omitempty"`
306+
// BasePath defines the base path on which the API is served, relative to the host.
307+
BasePath *string `json:"basePath,omitempty"`
308+
// Paths holds the available endpoints and their supported operations.
309+
Paths map[string]interface{} `json:"paths,omitempty"`
310+
// Info provides metadata about the API, such as title, version, and license.
311+
Info *SwaggerInfo `json:"info,omitempty"`
79312
}

0 commit comments

Comments
 (0)