Lightning.AdaptorService (Lightning v2.14.5-pre1)

View Source

The Adaptor Service is use to query and install adaptors in order to run jobs.

On startup, it queries the filesystem for package.json files and builds up a list of available adaptors.

Configuration

The service requires at least :adaptors_path, which is used to both query which adaptors are installed and when to install new adaptors.

Another optional setting is: :repo, which must point at a module that will be used to do the querying and installing.

Installing Adaptors

Using the install/2 function an adaptor can be installed, which will also add it to the list of available adaptors.

The adaptor is marked as :installing, to allow for conditional behaviour elsewhere such as delaying or rejecting processing until the adaptor becomes available.

Looking up adaptors

The module leans on Elixir's built-in Version module to provide version lookups.

When looking up an adaptor, either a string or a tuple can be used. In the case of requesting the latest version, any one of these will return the latest version the service is aware of.

  • @openfn/language-http
  • @openfn/language-http@latest
  • {"@openfn/language-http", nil}
  • {"@openfn/language-http", "latest"}
  • {~r/language-http/, "latest"}

You can also request a specific version, or use a range specification:

  • @openfn/language-http@1.2.3
  • {"@openfn/language-http", "~> 1.2.0"}
  • {"@openfn/language-http", "< 2.0.0"}

NOTE More complex npm style install strings like: ">=0.1.0 <0.2.0" are not supported. Generally the tuple style is preferred when using range specifications as the npm style strings have a simplistic regex splitter.

See Version for more details on matching versions.

Summary

Types

package_spec()

@type package_spec() :: {name :: String.t() | Regex.t(), version :: String.t() | nil}

Functions

build_aliased_name(arg)

Turns a package name and version into a string for NPM.

Since multiple versions of the same package can be installed, it's important to rely on npms built-in package aliasing.

E.g. @openfn/language-http@1.2.8 turns into:

 `@openfn/language-http-1.2.8@npm:@openfn/language-http@1.2.8`

Which is pretty long winded but necessary for the reason above.

If using this module as a base, it's likely you would need to adaptor this to suit your particular naming strategy.

child_spec(arg)

Returns a specification to start this module under a supervisor.

See Supervisor.

find_adaptor(agent, package)

@spec find_adaptor(Agent.agent(), package :: String.t()) ::
  Lightning.AdaptorService.Adaptor.t() | nil
@spec find_adaptor(Agent.agent(), package_spec()) ::
  Lightning.AdaptorService.Adaptor.t() | nil

get_adaptors(agent)

install(agent, package)

@spec install(Agent.agent(), binary()) ::
  {:ok, Lightning.AdaptorService.Adaptor.t()}
  | {:error, {Collectable.t(), exit_status :: non_neg_integer()}}
@spec install(Agent.agent(), package_spec()) ::
  {:ok, Lightning.AdaptorService.Adaptor.t()}
  | {:error, {Collectable.t(), exit_status :: non_neg_integer()}}

install!(agent, package_spec)

@spec install!(Agent.agent(), package_spec()) ::
  {:ok, Lightning.AdaptorService.Adaptor.t()}
  | {:error, {Collectable.t(), exit_status :: non_neg_integer()}}

installed?(agent, package_spec)

resolve_package_name(package_name)

start_link(opts)