From 039488972fdb844f7aaabb6c62045f2beed5645b Mon Sep 17 00:00:00 2001 From: JessamyT Date: Wed, 16 Oct 2024 23:34:13 -0700 Subject: [PATCH 1/2] DOCS-2543: Refactor registry initial commit --- .../registry/configure/edit-local-module.png | Bin 19845 -> 0 bytes .../registry/configure/ultrasonic-module.png | Bin 0 -> 51352 bytes .../configure/ultrasonic-resource.png | Bin 0 -> 87009 bytes docs/how-tos/upload-module.md | 2 +- docs/installation/viam-micro-server-dev.md | 2 +- docs/registry/_index.md | 100 +--- docs/registry/advanced/_index.md | 2 +- docs/registry/configure.md | 432 +++++++----------- docs/registry/examples/_index.md | 1 + 9 files changed, 162 insertions(+), 377 deletions(-) delete mode 100644 assets/registry/configure/edit-local-module.png create mode 100644 assets/registry/configure/ultrasonic-module.png create mode 100644 assets/registry/configure/ultrasonic-resource.png diff --git a/assets/registry/configure/edit-local-module.png b/assets/registry/configure/edit-local-module.png deleted file mode 100644 index 3317c5d797f9d0666134c47bb46a7a9ca3c2c364..0000000000000000000000000000000000000000 GIT binary patch literal 0 HcmV?d00001 literal 19845 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 fh{}A&Hg1%hroEi0hm^1IKw`( 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 a$VCm#zqB@-1}&`#ZY!wX$h&6j_x}Ka&p?O( literal 0 HcmV?d00001 diff --git a/docs/how-tos/upload-module.md b/docs/how-tos/upload-module.md index ecb543fd38..708b9f7b08 100644 --- a/docs/how-tos/upload-module.md +++ b/docs/how-tos/upload-module.md @@ -69,7 +69,7 @@ Select the private or public tab for instructions to upload your module with the {{< tabs >}} {{% tab name="Private" %}} -Get the `org-id` for your {{< glossary_tooltip term_id="organization" text="organization" >}} from your organization's **Settings** page in [the Viam App](https://app.viam.com/) and run the following command from the same directory as your custom module to generate metadata for your module: +Get the `org-id` for your {{< glossary_tooltip term_id="organization" text="organization" >}} from your organization's **Settings** page in [the Viam app](https://app.viam.com/) and run the following command from the same directory as your custom module to generate metadata for your module: ```sh {id="terminal-prompt" class="command-line" data-prompt="$"} viam module create --name --org-id diff --git a/docs/installation/viam-micro-server-dev.md b/docs/installation/viam-micro-server-dev.md index 621b9dcdce..64597bffd4 100644 --- a/docs/installation/viam-micro-server-dev.md +++ b/docs/installation/viam-micro-server-dev.md @@ -212,7 +212,7 @@ make upload 1. Develop the module by defining `structs` which implement the necessary `traits` and adding tests and registration hooks for them, per the walkthrough. 1. To consume the module, follow the "Create a Project" workflow in a different directory, and register your module in the `dependencies` section of the project's `Cargo.toml` file, then build and flash the project. - The module will now be available for use by adding it to your machine configuration on the [Viam App](https://app.viam.com). + The module will now be available for use by adding it to your machine configuration on the [Viam app](https://app.viam.com). {{% /tab %}} {{% tab name="viam-micro-server Development" %}} diff --git a/docs/registry/_index.md b/docs/registry/_index.md index d0d5199b7c..dac0688bdf 100644 --- a/docs/registry/_index.md +++ b/docs/registry/_index.md @@ -1,5 +1,5 @@ --- -title: "Extend Viam with Models from the Viam Registry" +title: "The Viam Registry" linkTitle: "Registry" weight: 600 type: "docs" @@ -15,7 +15,6 @@ tags: description: "Add additional models of components and services or ML models from the Viam Registry, or extend Viam by creating new modular resources." images: ["/platform/registry.svg"] no_list: true -modulescript: true aliases: - "/build/program/extend/modular-resources/" - "/extend/modular-resources/" @@ -26,111 +25,22 @@ aliases: menuindent: true --- -The [Viam registry](https://app.viam.com/registry) is the central place where you can browse: +The [Viam registry](https://app.viam.com/registry) is the storage and distribution system for: {{< cards >}} -{{% manualcard link="#modular-resources" %}} +{{% manualcard link="/registry/configure/" %}} **Modular resources** that add capabilities to your machine beyond what is built into `viam-server` {{% /manualcard %}} -{{% manualcard link="#ml-models" %}} +{{% manualcard link="/services/ml/ml-models/" %}} **ML models** to deploy with machine applications like computer vision {{% /manualcard %}} -{{% manualcard link="#ml-training-scripts" %}} +{{% manualcard link="/services/ml/training-scripts/" %}} **Training scripts** to train and produce ML models in the Viam cloud for custom machine learning {{% /manualcard %}} {{< /cards >}} - -## Modular resources - -

-{{}} -

- -Viam provides built-in support for a variety of {{< glossary_tooltip term_id="resource" text="resources" >}}: - -- Various types of hardware {{< glossary_tooltip term_id="component" text="components" >}}. -- High-level functionality exposed as {{< glossary_tooltip term_id="service" text="services" >}}. - -If the model of component or service you want to use for your project is not built into `viam-server` and available for configuration by default, you can use a {{< glossary_tooltip term_id="model" text="model" >}} from a {{< glossary_tooltip term_id="module" text="module" >}}. - -A module provides one or more {{< glossary_tooltip term_id="modular-resource" text="modular resources" >}}, and is packaged to streamline deployment to a Viam machine. -Modules run alongside [`viam-server`](/architecture/rdk/) as separate processes, communicating with `viam-server` over UNIX sockets. -When a module initializes, it registers its {{< glossary_tooltip term_id="model" text="model or models" >}} and associated [APIs](/appendix/apis/) with `viam-server`, making the new model available for use. - -To configure a modular resource on your robot, [add new models that others have created](/registry/configure/#add-a-modular-resource-from-the-viam-registry) from the [Viam registry](https://app.viam.com/registry) or [create your own](#create-your-own-modules). - -You can search the available modular resources from the Viam registry here: - -{{}} - -You can see details about each module in the [Viam registry](https://app.viam.com/registry) on its dedicated module page. -You can integrate modules into any Viam-powered machine. - -Be aware that unlike natively available models, modular resources are not documented on the Viam Documentation. -Documentation for each modular resource is available on its GitHub page, which is linked from the models' page on [the registry](https://app.viam.com/registry) or by clicking on the model name in the above search. - -## Use modules - -To use a modular resource from the registry, add it from your machine's **CONFIGURE** tab in the Viam app, using the **Create component** button. - -After adding a module to your machine, you can choose to [configure](/registry/configure/) it for automatic version updates from the Viam registry, or update your module manually. -By default, newly added modules will remain at the version they were when you installed them, and will not update automatically. - -Once you have added and configured the module you would like to use in the Viam app, you can test your added resource using the [**CONTROL** tab](/fleet/control/) and program it using [standardized APIs](/appendix/apis/). - -`viam-server` manages the [dependencies](/architecture/rdk/#dependency-management), [start-up](/architecture/rdk/#start-up), [reconfiguration](/architecture/rdk/#reconfiguration), [data management](/services/data/capture-sync/#configure-data-capture-and-sync), and [shutdown](/architecture/rdk/#shutdown) behavior of your modular resource. - -## Create your own modules - -If none of the existing modular resources in the Viam registry support your use case, you can create your own modules to provide your own modular resources: - -- **Implement a custom component**: Write a driver for an unsupported {{< glossary_tooltip term_id="component" text="component" >}} by implementing the corresponding component API. - -- **Implement a custom service**: Implement your own algorithm or {{< glossary_tooltip term_id="model" text="model" >}} against a corresponding service API or use custom algorithms or data models when working with services such as {{< glossary_tooltip term_id="slam" text="SLAM" >}}, vision, or motion planning. - -You can write modules in a variety of programming languages, such as, Go, Python, C++, Rust, while implementing the same [APIs](/appendix/apis/). - -To create a new module: - -1. [Create a module](/how-tos/create-module/) with one or more modular resources by implementing all methods for the component's or service's standardized API. -1. [Upload the module to the Viam registry](/how-tos/create-module//#upload-your-module-to-the-modular-resource-registry) to make it available for deployment to machines or add it as a [local module](/registry/configure/#local-modules). - You can upload _private_ modules for your {{< glossary_tooltip term_id="organization" text="organization" >}} or _public_ modules. -1. Once you have uploaded your module to the registry, [deploy and configure the module](/registry/configure/) from the Viam app. - Then, you can test your added resource using the [**CONTROL** tab](/fleet/control/) and [program](/sdks/) it with Viam's Go or Python SDKs. - -See the following how-to guide for full instructions, or one of our example tutorials: - -{{< cards >}} -{{% card link="/how-tos/create-module/" class="fit-contain" %}} -{{% card link="/tutorials/custom/custom-base-dog/" %}} -{{% card link="/registry/examples/custom-arm/" %}} -{{< /cards >}} - -## ML models - -Viam provides the ability to train, upload, and deploy [machine learning models](/services/ml/ml-models/) within the platform. -See [Machine Learning](/services/ml/) for more information. - -The Viam registry hosts trained ML models that users have made public, which you can use to deploy classifiers or detectors for your use case onto your robot instead of training your own. -You can also upload your own model to the registry. - -You can search the available ML models from the Viam registry here: - -{{}} - -To use an existing model from the registry, [deploy the ML model to your robot](/services/ml/deploy/) and use a [Vision service](/services/vision/) to make detections or classifications on-machine. - -## ML training scripts - -The Viam registry hosts custom Python ML training scripts, which you can use to train custom machine learning models. -You can upload your own training script by following the guide to [Train a Model with a Custom Python Training Script](/how-tos/create-custom-training-scripts/). - -You can search the available ML training scripts from the Viam registry here: - -{{}} diff --git a/docs/registry/advanced/_index.md b/docs/registry/advanced/_index.md index 6cc75ee5f8..bf726889d9 100644 --- a/docs/registry/advanced/_index.md +++ b/docs/registry/advanced/_index.md @@ -21,7 +21,7 @@ aliases: --- Some use cases may require advanced considerations when designing or deploying modular resources. -Depending on your needs, you may wish to define a new API subtype, deploy a custom component using a server on a {{< glossary_tooltip term_id="remote-part" text="remote" >}} {{< glossary_tooltip term_id="part" text="part" >}}, or design a custom ML model. +Depending on your needs, you may wish to define an entirely new API subtype, deploy a custom component using a server on a {{< glossary_tooltip term_id="remote-part" text="remote" >}} {{< glossary_tooltip term_id="part" text="part" >}}, or design a custom ML model. ## New API subtypes diff --git a/docs/registry/configure.md b/docs/registry/configure.md index 3d97c1840f..f287e2a2bb 100644 --- a/docs/registry/configure.md +++ b/docs/registry/configure.md @@ -1,6 +1,6 @@ --- -title: "Find a Module for your Machine" -linkTitle: "Find modules" +title: "Modular Resources" +linkTitle: "Modular Resources" weight: 10 type: "docs" tags: @@ -12,7 +12,7 @@ tags: "components", "services", ] -description: "Add a modular resource to your machine by configuring it." +description: "Integrate additional hardware or software functionality into your machine with modular resources." no_list: true icon: true images: ["/registry/create-module.svg"] @@ -21,130 +21,174 @@ aliases: - "/extend/modular-resources/configure/" - "/modular-resources/configure/" modulescript: true -toc_hide: true --- -You can extend Viam by adding a module on your machine that provides one or more {{< glossary_tooltip term_id="modular-resource" text="modular resources" >}} (components or services): +Viam provides built-in support for a variety of {{< glossary_tooltip term_id="resource" text="resources" >}}: -1. Add a {{< glossary_tooltip term_id="module" text="module" >}}, either one [from the registry](#add-a-modular-resource-from-the-viam-registry) or a [local module](#local-modules). - This makes the modular resource available to the machine. -1. Then add the modular resource itself. +- Various types of hardware {{< glossary_tooltip term_id="component" text="components" >}}. +- High-level functionality exposed as {{< glossary_tooltip term_id="service" text="services" >}}. -When you add a modular resource _from the registry_, the underlying module that provides it is automatically added at the same time. -To add a modular resource from a _local_ module, you must add the module first. +You can extend Viam beyond the built-in component and service models by adding a _{{< glossary_tooltip term_id="module" text="module" >}}_ on your machine. +A module provides one or more _{{< glossary_tooltip term_id="modular-resource" text="modular resources" >}}_, and is packaged to streamline deployment to a Viam machine. -You can search the available modular resources from the Viam Registry here: +{{< expand "How modules and modular resources work" >}} -{{}} - -You can see details about each module in the [Viam registry](https://app.viam.com/registry) on its dedicated module page. -You can integrate modules into any Viam-powered machine. +To use a modular resource from the registry, add it from your machine's **CONFIGURE** tab in the Viam app, using the **+** button. -## Add a modular resource from the Viam registry - -The [Viam registry](https://app.viam.com/registry) is a central repository of modules from both Viam and the robotics community that allows you to easily extend Viam's capabilities on your machine. - -A module provides one or more {{< glossary_tooltip term_id="resource" text="modular resources" >}}. - -Follow the instructions below depending on the type of modular resource you would like to add to your machine: +When you add a modular resource _from the registry_, the underlying module that provides it is automatically added at the same time. +To add a modular resource from a _local_ module, you must add the module first. -{{< alert title="Note" color="note" >}} -If you are using a [rented Viam rover](/appendix/try-viam/), adding modules is disabled for security purposes. -{{< /alert >}} +After adding a module to your machine, you can choose to [configure](/registry/configure/) it for automatic version updates from the Viam registry, or update your module manually. +By default, newly added modules will remain at the version they were when you installed them, and will not update automatically. -{{< tabs >}} -{{% tab name="Add a modular component" %}} +Once you have added and configured the module and corresponding modular resource you would like to use in the Viam app, you can test the modular resource using the [**CONTROL** tab](/fleet/control/) and program it using [standardized APIs](/appendix/apis/). -To add a modular {{< glossary_tooltip term_id="component" text="component" >}} from the Viam registry to your machine: +Modules run alongside [`viam-server`](/architecture/rdk/) as separate processes, communicating with `viam-server` over UNIX sockets. +When a module initializes, it registers its {{< glossary_tooltip term_id="model" text="model or models" >}} and associated [APIs](/appendix/apis/) with `viam-server`, making the new model available for use. +`viam-server` manages the [dependencies](/architecture/rdk/#dependency-management), [start-up](/architecture/rdk/#start-up), [reconfiguration](/architecture/rdk/#reconfiguration), [data management](/services/data/capture-sync/#configure-data-capture-and-sync), and [shutdown](/architecture/rdk/#shutdown) behavior of your modular resource. -1. Navigate to the **CONFIGURE** tab of your machine's page in [the Viam app](https://app.viam.com). -2. Click the **+** (Create) icon next to your machine part in the left-hand menu and select **Component**. -3. Browse the list of available component types, and select the specific modular component you'd like to add. +{{< /expand >}} - {{}} +## Browse existing modular resources - You can also start typing to search for a module by name or to narrow down your search results. +You can search the available modular resources from the Viam Registry here: - {{}} +{{}} -4. After selecting the modular component, enter a name or use the suggested name for your modular component and click **Create** to add it to your machine's configuration. +You can see details about each module in the [Viam registry](https://app.viam.com/registry) on its dedicated module page. +You can integrate modules into any Viam-powered machine. - {{}} +## Create your own modular resources - Be sure the modular component you select supports the [platform](/cli/#using-the---platform-argument) you intend to use it with, such as `linux arm64`. - You can see which platforms the module supports at bottom of the module information screen before you add it. +If none of the existing modular resources in the Viam registry support your use case, you can create your own modules to provide your own modular resources. -When you add a modular component from the registry, it appears on the **CONFIGURE** tab like any other component. +You can write modules in a variety of programming languages, such as, Go, Python, C++, Rust, while implementing the same [APIs](/appendix/apis/) as the built-in components and services. -If the component requires you to configure specific **Attributes**, navigate to the **CONFIGURE** tab and hover over the component in the machine {{< glossary_tooltip term_id="part" text="part" >}} tree in the upper left-hand corner. -Click on the **...** menu and select **Go to homepage** to view the specific attribute requirements on the module's GitHub page. +{{< cards >}} +{{% card link="/how-tos/create-module/" class="fit-contain" %}} +{{% card link="/how-tos/sensor-module/" class="fit-contain" %}} +{{< /cards >}} -To delete a modular component, navigate to the component's card on the **CONFIGURE** tab. -Click on the **...** icon and click **Delete**. -Confirm your selection. +## Add a modular resource to your machine -{{% /tab %}} +### Modular resource configuration -{{% tab name="Add a modular service" %}} +When you add components and services to your machine with the builder UI, you can select available modular resources from the Viam registry. +As you add them, Viam automatically also adds the module that provides the modular resource to your configuration. +The modular resource card allows you to configure attributes for the resource. +Check the module's GitHub Readme for information about available configuration attributes for a resource. +You can configure modules and their modular resources in the config builder or with JSON. -To add a modular {{< glossary_tooltip term_id="service" text="service" >}} from the Viam registry to your machine: +{{< tabs >}} +{{% tab name="Config Builder" %}} -1. Navigate to the **CONFIGURE** tab of your machine's page in [the Viam app](https://app.viam.com). -2. Click the **+** icon next to your machine part in the left-hand menu and select **Service**. -3. Browse the list of available service types and select the specific modular service you'd like to add. +The following image shows an example of a configured modular resource, specifically an ultrasonic sensor component. +This modular component is made available by the `ultrasonic` module, shown in the [next section](#module-configuration). - {{}} +{{}} - You can also start typing to search for a module by name or to narrow down your search results. +{{% /tab %}} +{{% tab name="JSON" %}} - {{}} +{{< tabs >}} +{{% tab name="JSON Example" %}} -4. After selecting the modular service, enter a name or use the suggested name for your modular service and click **Create** to add it to your machine's configuration. +```json {class="line-numbers linkable-line-numbers"} + "components": [ + { + "name": "sensor-1", + "model": "viam:ultrasonic:sensor", + "type": "sensor", + "namespace": "rdk", + "attributes": { + "trigger_pin": "13", + "echo_interrupt_pin": "15", + "board": "board-1", + "timeout_ms": 500 + }, + "depends_on": [] + } + ] +``` - {{}} +{{% /tab %}} +{{% tab name="JSON Template" %}} - Be sure the modular service you select supports the [platform](/cli/#using-the---platform-argument) you intend to use it with, such as `linux arm64`. - You can see which platforms the module supports at bottom of the module information screen before you add it. +```json {class="line-numbers linkable-line-numbers"} + "components": [ + { + "name": "", + "model": "::", + "type": "", + "namespace": "", + "attributes": { + "" + }, + "depends_on": [] + } + ] +``` -When you add a modular service from the registry, it appears on the **CONFIGURE** tab like any other service. +{{% /tab %}} +{{< /tabs >}} -If the service requires you to configure specific **Attributes**, navigate to the **CONFIGURE** tab and hover over the service in the machine {{< glossary_tooltip term_id="part" text="part" >}} tree in the upper left-hand corner. -Click on the **...** menu and select **Go to homepage** to view the specific attribute requirements on the module's GitHub page. +The following properties are available for modular resources: -To delete a modular service, navigate to the service's card on the **CONFIGURE** tab. -Click on the **...** menu and click **Delete**. -Confirm your selection. + +| Name | Type | Required? | Description | +| ---- | ---- | --------- | ----------- | +| `name` | string | **Required** | What you want to name this instance of your modular resource. | +| `namespace` | string | **Required** | The namespace of the API (the first part of the {{< glossary_tooltip term_id="api-namespace-triplet" text="API namespace triplet">}}). This will be `rdk` unless the module implements a [custom, non-standard API](/registry/advanced/). See [Valid API identifiers](/how-tos/create-module/#valid-api-identifiers). | +| `type` | string | **Required** | The {{< glossary_tooltip term_id="subtype" text="subtype">}} of the API (the third part of the {{< glossary_tooltip term_id="api-namespace-triplet" text="API namespace triplet">}}). See [Valid API identifiers](/how-tos/create-module/#valid-api-identifiers). | +| `model` | string | **Required** | The full {{< glossary_tooltip term_id="model-namespace-triplet" text="model namespace triplet">}} of the modular resource's {{< glossary_tooltip term_id="model" text="model" >}}. | +| `depends_on` | array | Optional | The `name` of components you want to confirm are available on your machine alongside your modular resource. Often a [board](/components/board/). Unnecessary if you coded [implicit dependencies](/architecture/rdk/#dependency-management). | {{% /tab %}} {{< /tabs >}} -### Add additional modular resources from a registry module +All standard properties for configuration, such as `attributes` and `depends_on`, are also supported for modular resources. +The attributes available vary depending on your implementation. +If the module requires you to configure specific attributes, click the **Readme** link in the module's configuration card to view the specific attribute requirements on the module's GitHub page. -Once you have [added a module](#add-a-modular-resource-from-the-viam-registry) from the Viam registry, you can add any number of the modular resources it provides to your machine by adding new components or services configured with your modular resource's {{< glossary_tooltip term_id="model" text="model" >}}. +### Module configuration -Follow the same steps as when you added the first modular resource, clicking **Create** and **Component** or **Service** as applicable. -You will be prompted to click **Add module** again while configuring the resource, though no duplicate module will be added to the `modules` section of the configuration. +{{< tabs >}} +{{% tab name="Config Builder" %}} -## Edit the configuration of a module from the Viam registry +The following image shows an example of a configured module in a machine's config. +This ultrasonic sensor modular component in the previous section is provided by the [module](https://app.viam.com/module/viam/ultrasonic) shown here. -### Edit modular resources +{{}} -You can edit the configuration of the modular resource or resources you have added from your module in the card matching the `name` you gave the resource when adding it on the **CONFIGURE** tab. +{{% /tab %}} +{{% tab name="JSON" %}} -If you prefer to use JSON, the following properties are available for all modular resources: +Examples: - -| Name | Type | Required? | Description | -| ---- | ---- | --------- | ----------- | -| `name` | string | **Required** | What you want to name this instance of your modular resource. | -| `namespace` | string | **Required** | The namespace of the API (the first part of the {{< glossary_tooltip term_id="api-namespace-triplet" text="API namespace triplet">}}). See [Valid API identifiers](/how-tos/create-module/#valid-api-identifiers) | -| `type` | string | **Required** | The {{< glossary_tooltip term_id="subtype" text="subtype">}} of the API (the third part of the {{< glossary_tooltip term_id="api-namespace-triplet" text="API namespace triplet">}}). See [Valid API identifiers](/how-tos/create-module/#valid-api-identifiers). | -| `model` | string | **Required** | The full {{< glossary_tooltip term_id="model-namespace-triplet" text="model namespace triplet">}} of the modular resource's {{< glossary_tooltip term_id="model" text="model" >}}. | -| `depends_on` | array | Optional | The `name` of components you want to confirm are available on your machine alongside your modular resource. Often a [board](/components/board/). Unnecessary if you coded [implicit dependencies](/architecture/rdk/#dependency-management). | +```json {class="line-numbers linkable-line-numbers"} + "modules": [ + { + "type": "registry", + "name": "viam_ultrasonic", + "module_id": "viam:ultrasonic", + "version": "0.0.2" + }, + { + "type": "registry", + "name": "viam_tflite_cpu", + "module_id": "viam:tflite_cpu", + "version": "latest" + }, + { + "type": "registry", + "name": "viam_raspberry-pi", + "module_id": "viam:raspberry-pi", + "version": "1.1.0" + }, + ] +``` -All standard properties for configuration, such as `attributes` and `depends_on`, are also supported for modular resources. -The `attributes` available vary depending on your implementation. -If the module requires you to configure specific **Attributes**, click the **Registry** link in the module's configuration card to view the specific attribute requirements on the module's GitHub page. +The config of both a module and a corresponding modular resource resembles the following: {{< tabs >}} {{% tab name="JSON Template" %}} @@ -154,9 +198,9 @@ If the module requires you to configure specific **Attributes**, click the **Reg "components": [ { "name": "", - "model": "::", + "model": "::", "type": "", - "namespace": "", + "namespace": "", "attributes": {}, "depends_on": [] } @@ -164,7 +208,7 @@ If the module requires you to configure specific **Attributes**, click the **Reg "modules": [ { "type": "registry", - "name": "", + "name": "_", "module_id": ":", "version": "" } @@ -177,13 +221,13 @@ If the module requires you to configure specific **Attributes**, click the **Reg The following is an example configuration for the [Intel Realsense module](https://app.viam.com/module/viam/realsense). The configuration adds `viam:camera:realsense` as a modular resource from the module `viam:realsense`. -The custom model is configured as a component with the name "my-realsense". +The custom model is configured as a component with the name `myRealsenseCamera1`. ```json {class="line-numbers linkable-line-numbers"} { "components": [ { - "name": "my-realsense", + "name": "myRealsenseCamera1", "model": "viam:camera:realsense", "type": "camera", "namespace": "rdk", @@ -207,26 +251,30 @@ The custom model is configured as a component with the name "my-realsense". {{% /tab %}} {{% /tabs %}} -### Edit the module - -You can also view and edit the configuration of a modular resource's underlying module from the **CONFIGURE** tab: - -1. Navigate to the **CONFIGURE** tab of your machine's page in [the Viam app](https://app.viam.com). -2. Scroll to the card with the name of the module, as indicated by its page in the [registry](https://app.viam.com/registry). +{{% /tab %}} +{{< /tabs >}} - This is the **Registry module** card, which lists the deployed version of the module and the latest version available. - Here you can [configure how a module updates](#configure-version-update-management-for-a-registry-module). +The following properties are configurable for each module: - {{}} + +| Name | Type | Required? | Description | +| ---- | ---- | --------- | ----------- | +| `version` | string | **Required** |

You can specify:

  • a specific version (X.Y.Z) of the module to use
  • to pin the module version to the newest release, so your machine automatically updates to the latest version of the module that is available or to the latest patch release of a configured minor (X.Y.\_) or major (X.\_) version.

| +| `type` | string | **Required** | `registry` or `local`, depending on whether the module is in the [Viam registry](https://app.viam.com/registry) or is only available [locally](/how-tos/create-module/#test-your-module-locally) on your computer. | +| `name` | string | **Required** | The module author's organization namespace, followed by an underscore, followed by the name of the module. `_` | +| `module_id` | string | **Required** | The module namespace, then a colon, then the name of the module. Identical to the first two pieces of the {{< glossary_tooltip term_id="model-namespace-triplet" text="model namespace triplet" >}} | - You can also use JSON mode to [configure environment variables](#use-environment-variables-with-a-registry-module) for your module. +### Further configuration options -### Configure version update management for a registry module +{{< expand "Configure version update management" >}} -When you add a module to your machine, you can also configure how that module updates itself when a newer version becomes available from the Viam registry. +You can configure how each module on your machine updates itself when a newer version becomes available from the Viam registry. By default, a newly-added module is set to pin to the specific patch release (**Patch (X.Y.Z)**) of the version you added, meaning that the module will _never automatically update itself_. To allow automatic module updates when a new version of the module becomes available in the Viam registry, set the **Pinned version type** for your module in its module card on the **CONFIGURE** tab. + +{{}} + The following update options are available: - **Patch (X.Y.Z)**: Do not update to any other version. @@ -248,10 +296,11 @@ For any version type other than **Patch (X.Y.Z)**, the module will upgrade as so If, for example, the module provides a motor component, and the motor is running, it will stop while the module upgrades. {{% /alert %}} -### Use environment variables with a registry module +{{< /expand >}} +{{< expand "Use environment variables with a registry module" >}} Some modules require that you set specific environment variables as part of configuration. -You can click the **Homepage** link in the upper-right corner of the module configuration card to view any specific requirements on the module's GitHub page. +You can click the **Readme** link in the upper-right corner of the module configuration card to view any specific requirements on the module's GitHub page. Module environment variables can be either: @@ -340,7 +389,7 @@ To configure a modular resource with an environment variable, navigate to the ** To delete an environment variable configuration, delete the `env` section from your smart machine's configuration. -#### Default environment variables +### Default environment variables When a module is instantiated, it has access to the following default environment variables: @@ -348,186 +397,11 @@ When a module is instantiated, it has access to the following default environmen | Name | Description | | ---- | ----------- | | `VIAM_HOME` | The root of the `viam-server` configuration.
Default: `$HOME/.viam` | -| `VIAM_MODULE_ROOT` | The root of the module install directory. The module process uses this directory as its current working directory (`cwd`). This variable is useful for file navigation that is relative to the root of the module. If you are using a [local module](#local-modules), you must set this value manually if your module requires it.
Example: `/opt/my-module/verxxxx-my-module/` | +| `VIAM_MODULE_ROOT` | The root of the module install directory. The module process uses this directory as its current working directory (`cwd`). This variable is useful for file navigation that is relative to the root of the module. If you are using a [local module](/how-tos/create-module/#test-your-module-locally), you must set this value manually if your module requires it.
Example: `/opt/my-module/verxxxx-my-module/` | | `VIAM_MODULE_DATA` | A persistent folder location a module can use to store data across reboots and versions. This location is a good place to store [python virtual environments](/sdks/python/python-venv/).
Example: `$VIAM_HOME/module-data/cloud-machine-id/my-module-name/` | | `VIAM_MODULE_ID` | The module ID of the module.
Example: `viam:realsense` | -## Local modules - -If you wish to add a module to your machine without uploading it to the Viam registry, you can add your module as a _local module_. - -You can add your own custom modules as local modules, or you can add pre-built modules written by other Viam users. - -### Prepare a local module - -First determine the module you wish to add as a local module: - -- If you are adding your own custom module, be sure that you have followed the steps to [create your own module](/how-tos/create-module/) to code and compile your module and generate an executable. -- If you are using a pre-built module, make sure you have installed the module and determined the filename of [the module's executable](/how-tos/create-module/#compile-or-package-your-module). - -Then, ensure that `viam-server` is able to find and run the executable: - -- Ensure that the module executable is saved to a location on the filesystem of your machine that `viam-server` can access. - For example, if you are running `viam-server` on an Raspberry Pi, you must save the module executable on the Pi's filesystem. -- Ensure that this file is executable (runnable) with the following command: - - ```shell - sudo chmod a+rx - ``` - -See the instructions to [compile your module into an executable](/how-tos/create-module/#compile-or-package-your-module) for more information. - -### Add a local module - -To add a local module on your machine, first add its module, then the component or service it implements: - -1. Navigate to the **CONFIGURE** tab of your machine's page in [the Viam app](https://app.viam.com). -1. Click the **+** (Create) icon next to your machine part in the left-hand menu and select **Local module**, then **Local module**. -1. Enter a **Name** for this instance of your module. -1. Enter the module's **Executable path**. - This path must be the absolute path on your machine's filesystem to either: - - the module's [executable file](/how-tos/create-module/#compile-or-package-your-module), such as `run.sh` or a compiled binary. - - a [packaged tarball](https://www.cs.swarthmore.edu/~newhall/unixhelp/howto_tar.html) of your module, ending in `.tar.gz` or `.tgz`. - If you are providing a tarball file in this field, be sure that your packaged tarball contains your module's [`meta.json` file](/cli/#the-metajson-file) within it. -1. Then, click the **Create** button, and click **Save** in the upper right corner to save your config. - - {{}} - - This example shows the configuration for adding a [CSI camera](https://github.com/viamrobotics/csi-camera/) as a local module. - -1. Still on your machine's **CONFIGURE** tab, click the **+** (Create) icon next to your machine part in the left-hand menu. - -1. Select **Local module**, then select **Local component** or **Local service**. - -1. Select the type of modular resource provided by your module, such as a [camera](/components/camera/), from the dropdown menu. - -1. Enter the {{< glossary_tooltip term_id="model-namespace-triplet" text="model namespace triplet">}} of your modular resource's {{< glossary_tooltip term_id="model" text="model" >}}. - If you are adding a pre-built modular resource, the model triplet should be provided for you in the module's documentation. - -1. Enter a name for this instance of your modular resource. - This name must be different from the module name. - - {{}} - -1. Click **Create** to create the modular resource provided by the local module. - -Once you've added your local module using steps 1-5, you can repeat steps 6-11 to add as many additional instances of your modular resource as you need. - -### Edit the configuration of a local module - -Once you have added a modular resource to your machine, you can view and edit the underlying module. - -Navigate to the **CONFIGURE** tab of your machine's page in [the Viam app](https://app.viam.com). -Local modules you have added to your machine are identifiable by name. -Locate a module's card in the part-resource hierarchy and click on it to expand. - -The following properties are available for modules: - - -| Name | Type | Required? | Description | -| ---- | ---- | --------- | ----------- | -| `name` | string | **Required**| Name of the module you are registering. | -| `executable_path` | string | **Required**| The absolute path to the executable on your machine's filesystem. | -| `type` | string | **Required**| Either `registry` or `local`. | - -{{< tabs >}} -{{% tab name="Config Builder" %}} - -{{}} - -{{% /tab %}} -{{% tab name="JSON Template" %}} - -To edit the raw JSON instead of using the config builder UI, click **{} JSON** in the upper left corner of the **CONFIGURE** tab. - -```json {class="line-numbers linkable-line-numbers"} -{ - "modules": [ - { - "name": "", - "executable_path": "/", - "type": "local" - } - ] -} -``` - -{{% /tab %}} -{{% /tabs %}} - -### Add a local modular resource - -Once you have added a local module to your machine, you can add any number of the {{< glossary_tooltip term_id="resource" text="resources" >}} provided by that module to your machine by adding new components or services that use your modular resource's {{< glossary_tooltip term_id="model" text="model" >}}. - -The following properties are available for modular resources: - - -| Name | Type | Required? | Description | -| ---- | ---- | --------- | ----------- | -| `name` | string | **Required** | A custom name for this instance of your modular resource. | -| `namespace` | string | **Required** | The namespace of the API (the first part of the {{< glossary_tooltip term_id="api-namespace-triplet" text="API namespace triplet">}}). See [Valid API identifiers](/how-tos/create-module/#valid-api-identifiers). | -| `type` | string | **Required** | The {{< glossary_tooltip term_id="subtype" text="subtype">}} of the API (the third part of the {{< glossary_tooltip term_id="api-namespace-triplet" text="API namespace triplet">}}). See [Valid API identifiers](/how-tos/create-module/#valid-api-identifiers). | -| `model` | string | **Required** | The full {{< glossary_tooltip term_id="model-namespace-triplet" text="model namespace triplet">}} of the modular resource's {{< glossary_tooltip term_id="model" text="model" >}}. | -| `depends_on` | array | Optional | The `name` of components you want to confirm are available on your machine alongside your modular resource. Often a [board](/components/board/). Unnecessary if you coded [implicit dependencies](/architecture/rdk/#dependency-management). | - -All standard properties for configuration, such as `attributes` and `depends_on`, are also supported for modular resources. -The `attributes` available vary depending on your implementation. - -{{< tabs >}} -{{% tab name="JSON Template" %}} - -```json {class="line-numbers linkable-line-numbers"} -{ - "components": [ - { - "namespace": "", - "type": "", - "model": "::", - "name": "", - "attributes": {}, - "depends_on": [] - } - ], - "modules": [ ... ] // < INSERT YOUR MODULE CONFIGURATION > -} -``` - -{{% /tab %}} -{{% tab name="JSON Example" %}} - -The following is an example configuration for a base modular resource implementation. -The configuration adds `acme:demo:mybase` as a modular resource from the module `my_base`. -The custom model is configured as a component with the name "my-custom-base-1". -You can send commands to the base according to the Viam [base API](/appendix/apis/components/base/#api): - -```json {class="line-numbers linkable-line-numbers"} -{ - "components": [ - { - "type": "board", - "name": "main-board", - "model": "pi" - }, - { - "type": "base", - "name": "my-custom-base-1", - "model": "acme:demo:mybase", - "namespace": "rdk", - "attributes": {}, - "depends_on": ["main-board"] - } - ], - "modules": [ - { - "name": "my-custom-base", - "executable_path": "/home/my_username/my_base/run.sh" - } - ] -} -``` - -{{% /tab %}} -{{% /tabs %}} +{{< /expand >}} ## Next steps diff --git a/docs/registry/examples/_index.md b/docs/registry/examples/_index.md index 7f77c5bda8..39fe69a177 100644 --- a/docs/registry/examples/_index.md +++ b/docs/registry/examples/_index.md @@ -6,6 +6,7 @@ description: "Tutorials and repositories with modular resources configuration ex weight: 70 type: "docs" no_list: true +draft: true images: ["/tutorials/intermode/rover_outside.png"] imageAlt: "A large black intermode rover controlled with CANBUS protocol chilling outside in the snow." tags: From 28498b51d2bac145227f67c101fd3943677fd822 Mon Sep 17 00:00:00 2001 From: Naomi Pentrel <5212232+npentrel@users.noreply.github.com> Date: Sun, 20 Oct 2024 13:33:29 +0200 Subject: [PATCH 2/2] Move training scripts and ml models --- .../add-component-by-category.png | Bin .../add-component-by-name.png | Bin .../add-component-screen.png | Bin .../add-local-module-create.png | Bin .../add-local-module-csi-cam.png | Bin .../add-service-by-category.png | Bin .../add-service-by-name.png | Bin .../add-service-screen.png | Bin .../deployed-module-with-component.png | Bin .../ultrasonic-module.png | Bin .../ultrasonic-resource.png | Bin docs/appendix/apis/services/ml.md | 2 +- docs/appendix/changelog.md | 8 +- docs/appendix/contributing.md | 2 +- docs/appendix/glossary/model.md | 2 +- docs/appendix/glossary/modular-resource.md | 7 +- docs/appendix/glossary/module.md | 2 +- docs/cli.md | 2 +- docs/configure/_index.md | 4 +- docs/fleet/fragments.md | 2 +- docs/how-tos/create-module.md | 14 +- docs/how-tos/detect-people.md | 2 +- docs/how-tos/image-data.md | 4 +- docs/how-tos/manage-modules.md | 4 +- docs/how-tos/performance-metrics.md | 2 +- docs/how-tos/sensor-module.md | 2 +- docs/how-tos/train-deploy-ml.md | 4 +- docs/platform.md | 2 +- docs/registry/_index.md | 6 +- docs/registry/advanced/_index.md | 2 +- .../advanced/iterative-development.md | 6 +- docs/registry/examples/_index.md | 1 - docs/registry/examples/custom-arm.md | 4 +- docs/registry/ml-models.md | 91 +++++++ .../{configure.md => modular-resources.md} | 247 ++++++------------ .../ml => registry}/training-scripts.md | 13 +- docs/services/data/dataset.md | 2 +- docs/services/ml/_index.md | 89 ++++--- docs/services/ml/deploy/_index.md | 2 +- docs/services/ml/ml-models.md | 94 ------- docs/services/ml/{deploy => }/tflite_cpu.md | 4 +- docs/services/slam/cartographer/_index.md | 1 - docs/services/vision/mlmodel.md | 6 +- .../controlling-an-intermode-rover-canbus.md | 2 +- .../tutorials/projects/verification-system.md | 2 +- layouts/shortcodes/modular-resources.html | 2 +- 46 files changed, 290 insertions(+), 349 deletions(-) rename assets/registry/{configure => modular-resources}/add-component-by-category.png (100%) rename assets/registry/{configure => modular-resources}/add-component-by-name.png (100%) rename assets/registry/{configure => modular-resources}/add-component-screen.png (100%) rename assets/registry/{configure => modular-resources}/add-local-module-create.png (100%) rename assets/registry/{configure => modular-resources}/add-local-module-csi-cam.png (100%) rename assets/registry/{configure => modular-resources}/add-service-by-category.png (100%) rename assets/registry/{configure => modular-resources}/add-service-by-name.png (100%) rename assets/registry/{configure => modular-resources}/add-service-screen.png (100%) rename assets/registry/{configure => modular-resources}/deployed-module-with-component.png (100%) rename assets/registry/{configure => modular-resources}/ultrasonic-module.png (100%) rename assets/registry/{configure => modular-resources}/ultrasonic-resource.png (100%) create mode 100644 docs/registry/ml-models.md rename docs/registry/{configure.md => modular-resources.md} (59%) rename docs/{services/ml => registry}/training-scripts.md (79%) delete mode 100644 docs/services/ml/ml-models.md rename docs/services/ml/{deploy => }/tflite_cpu.md (98%) diff --git a/assets/registry/configure/add-component-by-category.png b/assets/registry/modular-resources/add-component-by-category.png similarity index 100% rename from assets/registry/configure/add-component-by-category.png rename to assets/registry/modular-resources/add-component-by-category.png diff --git a/assets/registry/configure/add-component-by-name.png b/assets/registry/modular-resources/add-component-by-name.png similarity index 100% rename from assets/registry/configure/add-component-by-name.png rename to assets/registry/modular-resources/add-component-by-name.png diff --git a/assets/registry/configure/add-component-screen.png b/assets/registry/modular-resources/add-component-screen.png similarity index 100% rename from assets/registry/configure/add-component-screen.png rename to assets/registry/modular-resources/add-component-screen.png diff --git a/assets/registry/configure/add-local-module-create.png b/assets/registry/modular-resources/add-local-module-create.png similarity index 100% rename from assets/registry/configure/add-local-module-create.png rename to assets/registry/modular-resources/add-local-module-create.png diff --git a/assets/registry/configure/add-local-module-csi-cam.png b/assets/registry/modular-resources/add-local-module-csi-cam.png similarity index 100% rename from assets/registry/configure/add-local-module-csi-cam.png rename to assets/registry/modular-resources/add-local-module-csi-cam.png diff --git a/assets/registry/configure/add-service-by-category.png b/assets/registry/modular-resources/add-service-by-category.png similarity index 100% rename from assets/registry/configure/add-service-by-category.png rename to assets/registry/modular-resources/add-service-by-category.png diff --git a/assets/registry/configure/add-service-by-name.png b/assets/registry/modular-resources/add-service-by-name.png similarity index 100% rename from assets/registry/configure/add-service-by-name.png rename to assets/registry/modular-resources/add-service-by-name.png diff --git a/assets/registry/configure/add-service-screen.png b/assets/registry/modular-resources/add-service-screen.png similarity index 100% rename from assets/registry/configure/add-service-screen.png rename to assets/registry/modular-resources/add-service-screen.png diff --git a/assets/registry/configure/deployed-module-with-component.png b/assets/registry/modular-resources/deployed-module-with-component.png similarity index 100% rename from assets/registry/configure/deployed-module-with-component.png rename to assets/registry/modular-resources/deployed-module-with-component.png diff --git a/assets/registry/configure/ultrasonic-module.png b/assets/registry/modular-resources/ultrasonic-module.png similarity index 100% rename from assets/registry/configure/ultrasonic-module.png rename to assets/registry/modular-resources/ultrasonic-module.png diff --git a/assets/registry/configure/ultrasonic-resource.png b/assets/registry/modular-resources/ultrasonic-resource.png similarity index 100% rename from assets/registry/configure/ultrasonic-resource.png rename to assets/registry/modular-resources/ultrasonic-resource.png diff --git a/docs/appendix/apis/services/ml.md b/docs/appendix/apis/services/ml.md index ec57eb9e25..9e414fae66 100644 --- a/docs/appendix/apis/services/ml.md +++ b/docs/appendix/apis/services/ml.md @@ -11,7 +11,7 @@ images: ["/services/icons/ml.svg"] The ML model service API allows you to make inferences based on a provided ML model. -The [ML Model service](/services/ml/deploy/) supports the following methods: +The [ML Model service](/services/ml/) supports the following methods: {{< readfile "/static/include/services/apis/generated/mlmodel-table.md" >}} diff --git a/docs/appendix/changelog.md b/docs/appendix/changelog.md index 6496fb78db..528f599216 100644 --- a/docs/appendix/changelog.md +++ b/docs/appendix/changelog.md @@ -190,7 +190,7 @@ In addition to other improvements, your component, service, and other resource c {{% changelog date="2024-03-01" color="added" title="Additional ML models" %}} Viam has added support for the TensorFlow, PyTorch, and ONNX ML model frameworks, expanding upon the existing support for TensorFlow Lite models. -You can now upload your own ML model(/services/ml/ml-models/) using any of these frameworks for use with the Vision service. +You can now upload your own ML model(/registry/ml-models/) using any of these frameworks for use with the Vision service. {{% /changelog %}} @@ -229,7 +229,7 @@ You can now use the [generic service](/services/generic/) to define new, unique {{% changelog date="2024-02-12" color="added" title="ML models in the registry" %}} -You can now upload [machine learning (ML) models](/services/ml/ml-models/) to the Viam registry, in addition to modules. +You can now upload [machine learning (ML) models](/registry/ml-models/) to the Viam registry, in addition to modules. You may upload models you have trained yourself using the Viam app, or models you have trained outside of the App. When uploading, you have the option to make your model available to the general public for reuse. @@ -922,8 +922,8 @@ You will need to first register the machine learning model file with the [ML mod {{% changelog date="2023-03-31" color="added" title="Machine learning for image classification models" %}} -You can now [train](/how-tos/train-deploy-ml/) and [deploy](/services/ml/deploy/) image classification models with the [data management service](/services/data/) and use your machine's image data directly within Viam. -Additionally, you can upload and use existing [machine learning models](/services/ml/ml-models/) with your machines. +You can now [train](/how-tos/train-deploy-ml/) and [deploy](/services/ml/) image classification models with the [data management service](/services/data/) and use your machine's image data directly within Viam. +Additionally, you can upload and use existing [machine learning models](/registry/ml-models/) with your machines. For more information on using data synced to the cloud to train machine learning models, read [Train a model](/how-tos/train-deploy-ml/). {{% /changelog %}} diff --git a/docs/appendix/contributing.md b/docs/appendix/contributing.md index f005250377..c7e777c792 100644 --- a/docs/appendix/contributing.md +++ b/docs/appendix/contributing.md @@ -94,7 +94,7 @@ The docs use the [Diátaxis Framework](https://diataxis.fr/) as the basis of t - **How-to Guide (procedural)**: A task-oriented piece of content that directs a reader to perform actions step by step to complete a task, like instructions to sauté onions. Generally starts with a description of the task and things to consider, and then provides a set of numbered steps to follow. - For example, the [Installation page](/installation/viam-server-setup/) or the [Find module page](/registry/configure/). + For example, the [Installation page](/installation/viam-server-setup/) or the [Find module page](/registry/modular-resources/). {{< expand "Click to view template" >}} diff --git a/docs/appendix/glossary/model.md b/docs/appendix/glossary/model.md index 07673639b0..09568efbae 100644 --- a/docs/appendix/glossary/model.md +++ b/docs/appendix/glossary/model.md @@ -12,7 +12,7 @@ Models allow you to control hardware or software of a similar category, such as For example, some _models_ of DC motors communicate using [GPIO](/components/board/), while other DC motors use serial protocols like the SPI bus. Regardless, you can power any motor model that implements the `rdk:component:motor` API with the `SetPower()` method. -Models are either included with [`viam-server`](/architecture/rdk/), provided in {{< glossary_tooltip term_id="module" text="custom modules" >}} available for download from the [Viam registry](https://app.viam.com/registry), or installed as [local modules](/registry/configure/#local-modules). +Models are either included with [`viam-server`](/architecture/rdk/) or provided through {{< glossary_tooltip term_id="module" text="modules" >}}. All models are uniquely namespaced as colon-delimited-triplets. Built-in model names have the form `rdk:builtin:name`. Modular resource model names have the form `namespace:repo-name:name`. diff --git a/docs/appendix/glossary/modular-resource.md b/docs/appendix/glossary/modular-resource.md index ff91c2fbcb..ba46d4abf4 100644 --- a/docs/appendix/glossary/modular-resource.md +++ b/docs/appendix/glossary/modular-resource.md @@ -2,12 +2,11 @@ title: Modular Resource id: modular-resource full_link: /registry/ -short_description: A modular resource is a custom model of a component or service that implements the standardized API methods for that resource. +short_description: A modular resource is a model of a component or service provided by a module. --- -A modular resource is a custom {{< glossary_tooltip term_id="model" text="model" >}} of a {{< glossary_tooltip term_id="component" text="component" >}} or {{< glossary_tooltip term_id="service" text="service" >}} that implements the standardized [API methods](/appendix/apis/) for that {{< glossary_tooltip term_id="resource" text="resource" >}}. -Modular resources are provided by {{< glossary_tooltip term_id="module" text="modules" >}}, and are not built into `viam-server`. -A modular resource runs in the module process. +A modular resource is a {{< glossary_tooltip term_id="model" text="model" >}} of a {{< glossary_tooltip term_id="component" text="component" >}} or {{< glossary_tooltip term_id="service" text="service" >}} provided by a {{< glossary_tooltip term_id="module" text="module" >}}. +A modular resource runs in a module process. This differs from built-in resources, which run as part of `viam-server`. For more information see the [Modular Resource Documentation](/registry/). diff --git a/docs/appendix/glossary/module.md b/docs/appendix/glossary/module.md index 71a4715a02..3590b2644d 100644 --- a/docs/appendix/glossary/module.md +++ b/docs/appendix/glossary/module.md @@ -8,6 +8,6 @@ short_description: A module provides one or more modular resources, which add re A _module_ provides one or more {{< glossary_tooltip term_id="modular-resource" text="modular resources" >}}, which add {{< glossary_tooltip term_id="resource" text="resource" >}} {{< glossary_tooltip term_id="type" text="types" >}} or {{< glossary_tooltip term_id="model" text="models" >}} that are not built into Viam. Modules run alongside `viam-server` as separate process, communicating with `viam-server` over UNIX sockets. -You can [create your own module](/how-tos/create-module/) or [add existing modules from the Viam registry](/registry/configure/). +You can [create your own module](/how-tos/create-module/) or [add existing modules from the Viam registry](/registry/modular-resources/). For more information see the [modular resource documentation](/registry/). diff --git a/docs/cli.md b/docs/cli.md index 815c1d359a..1f1de04208 100644 --- a/docs/cli.md +++ b/docs/cli.md @@ -1248,7 +1248,7 @@ The `--stream` argument, when included in the CLI command prior to the `--data` ### `training-script` -Manage training scripts for [custom ML training](/services/ml/training-scripts/). +Manage training scripts for [custom ML training](/registry/training-scripts/). ```sh {class="command-line" data-prompt="$"} viam training-script upload --framework= --org-id= --path= --script-name= --type= diff --git a/docs/configure/_index.md b/docs/configure/_index.md index 667125d04b..d41cfaf82f 100644 --- a/docs/configure/_index.md +++ b/docs/configure/_index.md @@ -258,8 +258,10 @@ Find more information in the [processes documentation](/configure/processes/). Modules allow you to add [modular resources](/registry/) to your machines which add resource types or models that are not built into Viam. Many models are available in the [registry](https://app.viam.com/registry) and you are able to add them as components or services. +#### Local Modules + To add a module that is not in the registry and is local to your machine, click the **+** icon next to your {{< glossary_tooltip term_id="part" text="machine part" >}} in the left-hand menu of the **CONFIGURE** tab and select **Local module**. -Follow the instructions in our [registry documentation](/registry/configure/#add-a-local-module) to configure the module. +Follow the instructions in our [registry documentation](/registry/modular-resources/#configuration) to configure the module. ### Remote parts diff --git a/docs/fleet/fragments.md b/docs/fleet/fragments.md index 8cc3381001..62153d59c2 100644 --- a/docs/fleet/fragments.md +++ b/docs/fleet/fragments.md @@ -267,7 +267,7 @@ This example uses [`$set`](https://www.mongodb.com/docs/manual/reference/operato {{< /expand >}} {{< expand "Pin a module version" >}} -This example uses [`$set`](https://www.mongodb.com/docs/manual/reference/operator/update/set/#mongodb-update-up.-set) to set [version update settings for a module](/registry/configure/#edit-the-configuration-of-a-module-from-the-viam-registry) named `custom-sensor` in the fragment: +This example uses [`$set`](https://www.mongodb.com/docs/manual/reference/operator/update/set/#mongodb-update-up.-set) to set [version update settings for a module](/registry/modular-resources/#configuration) named `custom-sensor` in the fragment: ```json {class="line-numbers linkable-line-numbers"} "fragment_mods": [ diff --git a/docs/how-tos/create-module.md b/docs/how-tos/create-module.md index ee3bf8b15d..e2ac322f8d 100644 --- a/docs/how-tos/create-module.md +++ b/docs/how-tos/create-module.md @@ -22,7 +22,7 @@ cost: "0"
Viam provides built-in support for a variety of different {{< glossary_tooltip term_id="component" text="components" >}} and {{< glossary_tooltip term_id="service" text="services" >}}, as well as a registry full of {{< glossary_tooltip term_id="module" text="modules" >}} created by other users. -If no [existing modules](/registry/#modular-resources) support your specific use case, you can write your own [custom {{< glossary_tooltip term_id="resource" text="resources" >}}](/registry/) by creating a module, and either upload it to the [Viam registry](https://app.viam.com/registry) to share it publicly, or deploy it to your machine as a local module without uploading it to the registry. +If no [existing modules](/registry/modular-resources/) support your specific use case, you can write your own [custom {{< glossary_tooltip term_id="resource" text="resources" >}}](/registry/) by creating a module, and either upload it to the [Viam registry](https://app.viam.com/registry) to share it publicly, or deploy it to your machine as a local module without uploading it to the registry. Follow the instructions below to learn how to write a new module using your preferred language and its corresponding [Viam SDK](/sdks/), and then deploy it to your machines. @@ -199,7 +199,7 @@ For more Python module examples: - See the [Python SDK `examples` directory](https://github.com/viamrobotics/viam-python-sdk/tree/main/examples) for sample module code of varying complexity. - For tutorials featuring modular resource creation, see the [Modular resource examples](/registry/examples/) page. - For an example featuring a sensor, see [MCP300x](https://github.com/viam-labs/mcp300x-adc-sensor). -- For additional examples use the [modular resources search](/registry/#modular-resources) to search for examples of the model you are implementing, and click on the model's link to be able to browse its code. +- For additional examples use the [modular resources search](/registry/modular-resources/) to search for examples of the model you are implementing, and click on the model's link to be able to browse its code. {{% /tab %}} {{% tab name="Go" %}} @@ -214,7 +214,7 @@ For more Python module examples: For more Go module examples: - See the [Go SDK `examples` directory](https://github.com/viamrobotics/rdk/blob/main/examples/) for sample module code of varying complexity. -- For additional examples use the [modular resources search](/registry/#modular-resources) to search for examples of the model you are implementing, and click on the model's link to be able to browse its code. +- For additional examples use the [modular resources search](/registry/modular-resources/) to search for examples of the model you are implementing, and click on the model's link to be able to browse its code. {{% /tab %}} {{% tab name="C++" %}} @@ -685,7 +685,7 @@ func (b *myBase) Close(ctx context.Context) error { {{< alert title="Note" color="note" >}} For an example featuring a sensor, see [MCP3004-8](https://github.com/mestcihazal/mcp3004-8-go). -For additional examples use the [modular resources search](/registry/#modular-resources) to search for examples of the model you are implementing, and click on the model's link to be able to browse its code. +For additional examples use the [modular resources search](/registry/modular-resources/) to search for examples of the model you are implementing, and click on the model's link to be able to browse its code. {{< /alert >}} When implementing built-in methods from the Viam Go SDK in your model, be sure your implementation of those methods returns any values designated in the built-in method's return signature, typed correctly. @@ -1478,7 +1478,7 @@ Strings of the form `` indicate placeholders that you need to replace ````md # [`` module]() -This [module](https://docs.viam.com/registry/#modular-resources) implements the [`` API] in an model. +This [module](https://docs.viam.com/registry/modular-resources/) implements the [`` API] in an model. With this model, you can... ## Requirements @@ -1639,7 +1639,7 @@ Add the module to your machine's config, then add the component or service it im 1. Enter the {{< glossary_tooltip term_id="model-namespace-triplet" text="model namespace triplet">}} of your modular resource's {{< glossary_tooltip term_id="model" text="model" >}}. - {{}} + {{}} 1. Enter a name for this instance of your modular resource. This name must be different from the module name. @@ -1662,7 +1662,7 @@ See [How to Upload a Module](/how-tos/upload-module/) for instructions. You have now created a module, and are ready to deploy it to a fleet of machines. There are two ways to deploy a module: -- Through the Viam registry: Once you have uploaded your new module to the Viam registry, [add the module to one or more machines in the Viam app](/registry/configure/). +- Through the Viam registry: Once you have uploaded your new module to the Viam registry, [add the module to one or more machines in the Viam app](/registry/modular-resources/). You can also choose to configure [automated uploads for new module versions](/how-tos/manage-modules/#update-an-existing-module-using-a-github-action) through a continuous integration (CI) workflow, using a GitHub Action if desired, greatly simplifying how you push changes to your module to the registry as you make them. - As a local module (without uploading it to the Viam app), as you did in the [Test your module locally step above](#test-your-module-locally). This is a great way to test, but if you'd like to use the module on more machines it's easiest to add it to the registry either publicly or privately. diff --git a/docs/how-tos/detect-people.md b/docs/how-tos/detect-people.md index c713303172..0c0cd5608c 100644 --- a/docs/how-tos/detect-people.md +++ b/docs/how-tos/detect-people.md @@ -122,7 +122,7 @@ In the resulting ML model service configuration pane, ensure that **Deploy model Then click on **Select model**, switch to the **Registry** tab and select the **people** model by **ml-models-scuttle** to deploy a model that has been trained to be able to detect people. This model is a TFLite model. -For more detailed information, including optional attribute configuration, see the [`tflite_cpu` docs](/services/ml/deploy/tflite_cpu/). +For more detailed information, including optional attribute configuration, see the [`tflite_cpu` docs](/services/ml/tflite_cpu/). {{% /expand%}} {{%expand "Step 5: Configure a vision service" %}} diff --git a/docs/how-tos/image-data.md b/docs/how-tos/image-data.md index ef275376d9..8e79eef800 100644 --- a/docs/how-tos/image-data.md +++ b/docs/how-tos/image-data.md @@ -140,11 +140,11 @@ Contributors have written several filtering {{< glossary_tooltip term_id="module The following steps use the [`filtered_camera`](https://github.com/erh/filtered_camera) module: {{< table >}} -{{% tablestep link="/services/ml/deploy/"%}} +{{% tablestep link="/services/ml/"%}} {{}} **1. Add an ML model service to your machine** -Add an ML model service on your machine that is compatible with the ML model you want to use, for example [TFLite CPU](/services/ml/deploy/tflite_cpu/). +Add an ML model service on your machine that is compatible with the ML model you want to use, for example [TFLite CPU](/services/ml/tflite_cpu/). {{% /tablestep %}} {{% tablestep link="/services/vision/"%}} diff --git a/docs/how-tos/manage-modules.md b/docs/how-tos/manage-modules.md index 0f01f14fa4..6cd8d8172b 100644 --- a/docs/how-tos/manage-modules.md +++ b/docs/how-tos/manage-modules.md @@ -30,7 +30,7 @@ After you [create and deploy a module](/how-tos/create-module/), you may need to {{% /alert %}} -For information on pinning module deployments to versions, see [Configuring version update management for a registry module](/registry/configure/#configure-version-update-management-for-a-registry-module). +For information on pinning module deployments to versions, see [Module versioning](/registry/modular-resources/#module-versioning). ## Update an existing module @@ -425,7 +425,7 @@ To upload another version, you must increment the version number to a later vers ## Next steps {{< cards >}} -{{% manualcard link="/registry/configure/#configure-version-update-management-for-a-registry-module" %}} +{{% manualcard link="/registry/modular-resources/#module-versioning" %}} {{}}
diff --git a/docs/how-tos/performance-metrics.md b/docs/how-tos/performance-metrics.md index e318635845..bfb645a943 100644 --- a/docs/how-tos/performance-metrics.md +++ b/docs/how-tos/performance-metrics.md @@ -59,7 +59,7 @@ You must run `viam-server` with `sudo` to monitor machine performance metrics. ## Add the telegraf-sensor {{< table >}} -{{% tablestep link="/registry/configure/#add-a-modular-resource-from-the-viam-registry" %}} +{{% tablestep link="/registry/modular-resources/#configuration" %}} **1. Add the performance metrics sensor** On your machine's **CONFIGURE** page, click the **+** icon next to your machine part in the left-hand menu and select **Component**. diff --git a/docs/how-tos/sensor-module.md b/docs/how-tos/sensor-module.md index 68c894db99..b376ebcafa 100644 --- a/docs/how-tos/sensor-module.md +++ b/docs/how-tos/sensor-module.md @@ -444,7 +444,7 @@ With this model, you can gather [Open-Meteo](https://open-meteo.com/en/docs/air- ## Build and Run -To use this module, follow these instructions to [add a module from the Viam Registry](https://docs.viam.com/registry/configure/#add-a-modular-resource-from-the-viam-registry) and select the `rdk:sensor:jessamy:weather:meteo_PM` model from the [`jessamy:weather:meteo_PM` module](https://app.viam.com/module/rdk/jessamy:weather:_PM). +To use this module, add it from the machines **CONFIGURE** tab and select the `rdk:sensor:jessamy:weather:meteo_PM` model from the [`jessamy:weather:meteo_PM` module](https://app.viam.com/module/rdk/jessamy:weather:_PM). ## Configure your `meteo_PM` sensor diff --git a/docs/how-tos/train-deploy-ml.md b/docs/how-tos/train-deploy-ml.md index 2524c2cedb..364a64da5a 100644 --- a/docs/how-tos/train-deploy-ml.md +++ b/docs/how-tos/train-deploy-ml.md @@ -476,7 +476,7 @@ In the Viam app, navigate to your list of [**DATASETS**](https://app.viam.com/da Click **Train model** and follow the prompts. -You can train your model using **Built-in training** or using a [training script](/services/ml/training-scripts/) from the Viam Registry. +You can train your model using **Built-in training** or using a [training script](/registry/training-scripts/) from the Viam Registry. Click **Next steps**. @@ -559,7 +559,7 @@ On its own the ML model service only runs the model. To use it to make inferences on a camera stream, you need to use it alongside a vision service. {{< table >}} -{{% tablestep link="/services/ml/deploy/" %}} +{{% tablestep link="/services/ml/" %}} {{}} **1. Deploy your ML model** diff --git a/docs/platform.md b/docs/platform.md index 5dd7d1189c..7b78a2ecd8 100644 --- a/docs/platform.md +++ b/docs/platform.md @@ -60,7 +60,7 @@ And you can use the following platform capabilities and services to make your ma {{< cards >}} {{% relatedcard link="/services/data" %}} -{{% relatedcard link="/services/ml/deploy" alt_title="Machine Learning" %}} +{{% relatedcard link="/services/ml" alt_title="Machine Learning" %}} {{% relatedcard link="/services/motion" %}} {{% relatedcard link="/services/navigation" %}} {{% relatedcard link="/services/slam" %}} diff --git a/docs/registry/_index.md b/docs/registry/_index.md index dac0688bdf..f36924725e 100644 --- a/docs/registry/_index.md +++ b/docs/registry/_index.md @@ -28,17 +28,17 @@ menuindent: true The [Viam registry](https://app.viam.com/registry) is the storage and distribution system for: {{< cards >}} -{{% manualcard link="/registry/configure/" %}} +{{% manualcard link="/registry/modular-resources/" %}} **Modular resources** that add capabilities to your machine beyond what is built into `viam-server` {{% /manualcard %}} -{{% manualcard link="/services/ml/ml-models/" %}} +{{% manualcard link="/registry/ml-models/" %}} **ML models** to deploy with machine applications like computer vision {{% /manualcard %}} -{{% manualcard link="/services/ml/training-scripts/" %}} +{{% manualcard link="/registry/training-scripts/" %}} **Training scripts** to train and produce ML models in the Viam cloud for custom machine learning diff --git a/docs/registry/advanced/_index.md b/docs/registry/advanced/_index.md index bf726889d9..f9db631690 100644 --- a/docs/registry/advanced/_index.md +++ b/docs/registry/advanced/_index.md @@ -47,6 +47,6 @@ However, if you are unable to use [modular resources](/registry/) because you ne ## Design a custom ML model -When working with the [ML model service](/services/ml/), you can deploy an [existing model](/services/ml/ml-models/) or [train your own model](/how-tos/train-deploy-ml/). +When working with the [ML model service](/services/ml/), you can deploy an [existing model](/registry/ml-models/) or [train your own model](/how-tos/train-deploy-ml/). However, if you are writing your own {{< glossary_tooltip term_id="module" text="module" >}} that uses the ML model service together with the [vision service](/services/vision/), you can also [design your own ML model](/registry/advanced/mlmodel-design/) to better match your specific use case. diff --git a/docs/registry/advanced/iterative-development.md b/docs/registry/advanced/iterative-development.md index 990d3fc7a7..35f4d8734d 100644 --- a/docs/registry/advanced/iterative-development.md +++ b/docs/registry/advanced/iterative-development.md @@ -18,7 +18,7 @@ Generally, when developing a module, you have two options for iterative developm - **Sync Code and Test Remotely:** If you want your module to support a different architecture than your development workstation, you can sync your module code to a machine running your desired target architecture and test remotely. For example, if you are developing a module on a macOS computer, but want your module to support a Raspberry Pi running Linux on the `arm64` architecture, you can set up syncing for your module code to be able to continue development on your macOS workstation, but test on your remote Raspberry Pi. -Both of these options involve deploying your module to the target test system as a [local module](/registry/configure/#local-modules), without uploading it to the Viam registry. +Both of these options involve deploying your module to the target test system as a [local module](/configure/#local-modules), without uploading it to the Viam registry. Even if you have already published a version of your module to the registry, you might still find it useful to follow the steps in this section to verify that changes you make as part of releasing a new version work as expected on your target platform. Then, once you have tested it, you can [upload your module](/how-tos/upload-module/) to the Viam registry. @@ -35,7 +35,7 @@ If you are developing a module for the same target architecture as your developm 1. If you are using a programming language that requires that you build your module, such as Go or C++, follow the instructions for your language to [compile or package](/how-tos/create-module/#compile-or-package-your-module) your module. If you are using a programming language that does not require compilation, such as Python, you can skip this step. -1. Navigate to the Viam app, select your machine, and [add your module as a local module](/registry/configure/#local-modules) to your machine. +1. Navigate to the Viam app, select your machine, and [add your module as a local module](/configure/#local-modules) to your machine. For the **Executable path** field, enter the absolute path on your machine's filesystem to either: - the module's [executable file](/how-tos/create-module/#compile-or-package-your-module), such as `run.sh` or a compiled binary. @@ -171,7 +171,7 @@ If you are developing a module for a different target architecture than your dev 1. If you are using a programming language that requires that you build your module, such as Go or C++, follow the instructions for your language to [compile or package](/how-tos/create-module/#compile-or-package-your-module) your module. If you are using a programming language that does not require compilation, such as Python, you can skip this step. -1. Navigate to the Viam app, select your machine, and [add your module as a local module](/registry/configure/#local-modules) to your machine. +1. Navigate to the Viam app, select your machine, and [add your module as a local module](/configure/#local-modules) to your machine. Provide the **Executable path** in the configuration, pointing to the compiled or built binary, or the executable script, depending on your language. Provide the _remote system's_ path to this file, for example: /home/username/my-module/run.sh. With the Mutagen sync in place, Mutagen transfers the binary or executable automatically when you created it in the previous step. diff --git a/docs/registry/examples/_index.md b/docs/registry/examples/_index.md index 39fe69a177..7f77c5bda8 100644 --- a/docs/registry/examples/_index.md +++ b/docs/registry/examples/_index.md @@ -6,7 +6,6 @@ description: "Tutorials and repositories with modular resources configuration ex weight: 70 type: "docs" no_list: true -draft: true images: ["/tutorials/intermode/rover_outside.png"] imageAlt: "A large black intermode rover controlled with CANBUS protocol chilling outside in the snow." tags: diff --git a/docs/registry/examples/custom-arm.md b/docs/registry/examples/custom-arm.md index c57d81196d..d79f764021 100644 --- a/docs/registry/examples/custom-arm.md +++ b/docs/registry/examples/custom-arm.md @@ -237,7 +237,7 @@ The best practice with the Python SDK is to put `pass` or raise an `NotImplement ### Prepare the module for execution -To [add a module](/registry/configure/) to the configuration of your machine, you need to have an [executable](https://en.wikipedia.org/wiki/Executable) that: +To [add a module](/registry/modular-resources/) to the configuration of your machine, you need to have an [executable](https://en.wikipedia.org/wiki/Executable) that: - runs your module when executed, - takes a local socket as a command line argument, and @@ -270,4 +270,4 @@ Your executable will be run by `viam-server` as root, so dependencies need to be ## Configure the module and modular resource on your machine -Follow [these configuration instructions](/registry/configure/) to add your custom resource to your machine. +Follow [these configuration instructions](/registry/modular-resources/) to add your custom resource to your machine. diff --git a/docs/registry/ml-models.md b/docs/registry/ml-models.md new file mode 100644 index 0000000000..b9d99617d1 --- /dev/null +++ b/docs/registry/ml-models.md @@ -0,0 +1,91 @@ +--- +title: "ML Models" +linkTitle: "ML Models" +weight: 20 +type: "docs" +tags: ["data management", "ml", "model training"] +images: ["/services/ml/train-model.gif"] +videos: ["/services/ml/train-model.webm","/services/ml/train-model.mp4"] +videoAlt: "Add a bounding box around the dog in an image." +aliases: + - /data/train-model/ +description: "The Viam Registry provides ML models that can recognize patterns in your data. You can use them on your machines to interpret the machine's surroundings." +aliases: + - /services/ml/upload-model/ + - /services/ml/edit/ + - /ml/edit/ + - /manage/data/upload-model/ + - /manage/ml/upload-model/ + - /ml/upload-model/ + - /services/ml/ml-models/ +date: "2024-10-20" +modulescript: true +# SME: Tahiya + Alexa Greenberg +--- + +The Viam Registry provides Machine Learning (ML) models that can recognize patterns in your data. + +{{< alert title="In this page" color="note" >}} +{{% toc %}} +{{< /alert >}} + +## ML models in the registry + +{{}} + +## Usage + +To use an ML model with a machine, you have to deploy it using the [ML model service](/services/ml/). +Services like the [vision service](/services/vision/mlmodel/) can then use the ML model service to provide your machine with information about its surroundings. + +{{< alert title="Add support for other models" color="tip" >}} +ML models must be designed in particular shapes to work with the `mlmodel` [classification](/services/vision/mlmodel/) or [detection](/services/vision/mlmodel/) model of Viam's [vision service](/services/vision/). +See [ML Model Design](/registry/advanced/mlmodel-design/) to design modular ML model service with models that work with vision. +{{< /alert >}} + +## Versions + +When you deploy a model to a machine, Viam automatically deploys the `latest` version of the model to the machine. +This also means that as new version of the ML model become available, the machine will automatically get the latest version. + +If you do not want Viam to automatically deploy the `latest` version of the model, you can change the `packages` configuration in the [JSON machine configuration](/configure/#the-configure-tab) to use a specific version: + +```json +{ + "package": "/", + "version": "YYYY-MM-DDThh-mm-ss", + "name": "", + "type": "ml_model" +} +``` + +For models you have uploaded or traines, you can get the version number from a specific model version by navigating to the [models page](https://app.viam.com/data/models) finding the model's row, clicking on the right-side menu marked with **_..._** and selecting **Copy package JSON**. For example: `2024-02-28T13-36-51`. + +## Model framework support + +Viam currently supports the following frameworks: + + +| Model Framework | ML Model Service | Hardware Support | System Architecture | Description | +| --------------- | --------------- | ---------------- | ------------------- | ----------- | +| [TensorFlow Lite](https://www.tensorflow.org/lite) | [`tflite_cpu`](/services/ml/tflite_cpu/) | Any CPU
Nvidia GPU | Linux, Raspbian, MacOS, Android | Quantized version of TensorFlow that has reduced compatibility for models but supports more hardware. Uploaded models must adhere to the [model requirements](/services/ml/tflite_cpu/#model-requirements). | +| [ONNX](https://onnx.ai/) | [`onnx_cpu`](https://github.com/viam-labs/onnx-cpu) | Any CPU
Nvidia GPU | Android, MacOS, Linux arm-64 | Universal format that is not optimized for hardware inference but runs on a wide variety of machines. | +| [TensorFlow](https://www.tensorflow.org/) | [`triton`](https://github.com/viamrobotics/viam-mlmodelservice-triton) | Nvidia GPU | Linux (Jetson) | A full framework that is made for more production-ready systems. | +| [PyTorch](https://pytorch.org/) | [`triton`](https://github.com/viamrobotics/viam-mlmodelservice-triton) | Nvidia GPU | Linux (Jetson) | A full framework that was built primarily for research. Because of this, it is much faster to do iterative development with (model doesn’t have to be predefined) but it is not as “production ready” as TensorFlow. It is the most common framework for OSS models because it is the go-to framework for ML researchers. | + +## Next steps + +Use the ML model service to deploy a model to your machine or learn how to train and deploy models: + +{{< cards >}} +{{% card link="/services/ml/" customTitle="ML model service" %}} +{{% card link="/how-tos/train-deploy-ml/" %}} +{{< /cards >}} + +To see machine learning in actions, follow one of these tutorials: + +{{< cards >}} +{{% card link="/tutorials/projects/helmet/" %}} +{{% card link="/tutorials/services/color-detection-scuttle/" %}} +{{% card link="/tutorials/projects/integrating-viam-with-openai/" customDescription="Add object detection, speech recognition, natural language processing, and speech synthesis capabilities to a machine." %}} +{{< /cards >}} diff --git a/docs/registry/configure.md b/docs/registry/modular-resources.md similarity index 59% rename from docs/registry/configure.md rename to docs/registry/modular-resources.md index f287e2a2bb..5ce0d6d883 100644 --- a/docs/registry/configure.md +++ b/docs/registry/modular-resources.md @@ -20,72 +20,42 @@ aliases: - "program/extend/modular-resources/configure/" - "/extend/modular-resources/configure/" - "/modular-resources/configure/" + - /registry/configure/ +date: "2024-10-20" modulescript: true --- -Viam provides built-in support for a variety of {{< glossary_tooltip term_id="resource" text="resources" >}}: +The Viam Registry hosts {{< glossary_tooltip term_id="module" text="modules" >}} that provide modular resources. +A modular resource is a model of a {{< glossary_tooltip term_id="component" text="components" >}} or {{< glossary_tooltip term_id="service" text="services" >}} that you can use on your machines. -- Various types of hardware {{< glossary_tooltip term_id="component" text="components" >}}. -- High-level functionality exposed as {{< glossary_tooltip term_id="service" text="services" >}}. +{{< alert title="In this page" color="note" >}} +{{% toc %}} +{{< /alert >}} -You can extend Viam beyond the built-in component and service models by adding a _{{< glossary_tooltip term_id="module" text="module" >}}_ on your machine. -A module provides one or more _{{< glossary_tooltip term_id="modular-resource" text="modular resources" >}}_, and is packaged to streamline deployment to a Viam machine. - -{{< expand "How modules and modular resources work" >}} - -To use a modular resource from the registry, add it from your machine's **CONFIGURE** tab in the Viam app, using the **+** button. - -When you add a modular resource _from the registry_, the underlying module that provides it is automatically added at the same time. -To add a modular resource from a _local_ module, you must add the module first. - -After adding a module to your machine, you can choose to [configure](/registry/configure/) it for automatic version updates from the Viam registry, or update your module manually. -By default, newly added modules will remain at the version they were when you installed them, and will not update automatically. - -Once you have added and configured the module and corresponding modular resource you would like to use in the Viam app, you can test the modular resource using the [**CONTROL** tab](/fleet/control/) and program it using [standardized APIs](/appendix/apis/). - -Modules run alongside [`viam-server`](/architecture/rdk/) as separate processes, communicating with `viam-server` over UNIX sockets. -When a module initializes, it registers its {{< glossary_tooltip term_id="model" text="model or models" >}} and associated [APIs](/appendix/apis/) with `viam-server`, making the new model available for use. -`viam-server` manages the [dependencies](/architecture/rdk/#dependency-management), [start-up](/architecture/rdk/#start-up), [reconfiguration](/architecture/rdk/#reconfiguration), [data management](/services/data/capture-sync/#configure-data-capture-and-sync), and [shutdown](/architecture/rdk/#shutdown) behavior of your modular resource. - -{{< /expand >}} - -## Browse existing modular resources - -You can search the available modular resources from the Viam Registry here: +## Modular resources in the registry {{}} -You can see details about each module in the [Viam registry](https://app.viam.com/registry) on its dedicated module page. -You can integrate modules into any Viam-powered machine. - -## Create your own modular resources - -If none of the existing modular resources in the Viam registry support your use case, you can create your own modules to provide your own modular resources. +## Configuration -You can write modules in a variety of programming languages, such as, Go, Python, C++, Rust, while implementing the same [APIs](/appendix/apis/) as the built-in components and services. - -{{< cards >}} -{{% card link="/how-tos/create-module/" class="fit-contain" %}} -{{% card link="/how-tos/sensor-module/" class="fit-contain" %}} -{{< /cards >}} +When you add components and services from your machine's **CONFIGURE** tab, you can select available modular resources from the Viam registry. +When you add a modular resource _from the registry_, the module that provides it is automatically added at the same time. +To add a modular resource from a _local_ module, you must add the module first. -## Add a modular resource to your machine +You configure the module and the modular resources it provides separately. ### Modular resource configuration -When you add components and services to your machine with the builder UI, you can select available modular resources from the Viam registry. -As you add them, Viam automatically also adds the module that provides the modular resource to your configuration. The modular resource card allows you to configure attributes for the resource. -Check the module's GitHub Readme for information about available configuration attributes for a resource. -You can configure modules and their modular resources in the config builder or with JSON. {{< tabs >}} {{% tab name="Config Builder" %}} The following image shows an example of a configured modular resource, specifically an ultrasonic sensor component. -This modular component is made available by the `ultrasonic` module, shown in the [next section](#module-configuration). +This modular component is made available by the `ultrasonic` module. +See [module configuration](#module-configuration). -{{}} +{{}} {{% /tab %}} {{% tab name="JSON" %}} @@ -94,71 +64,64 @@ This modular component is made available by the `ultrasonic` module, shown in th {{% tab name="JSON Example" %}} ```json {class="line-numbers linkable-line-numbers"} - "components": [ - { - "name": "sensor-1", - "model": "viam:ultrasonic:sensor", - "type": "sensor", - "namespace": "rdk", - "attributes": { - "trigger_pin": "13", - "echo_interrupt_pin": "15", - "board": "board-1", - "timeout_ms": 500 - }, - "depends_on": [] - } - ] +{ + "name": "sensor-1", + "model": "viam:ultrasonic:sensor", + "type": "sensor", + "namespace": "rdk", + "attributes": { + "trigger_pin": "13", + "echo_interrupt_pin": "15", + "board": "board-1", + "timeout_ms": 500 + }, + "depends_on": [] +} ``` {{% /tab %}} {{% tab name="JSON Template" %}} ```json {class="line-numbers linkable-line-numbers"} - "components": [ - { - "name": "", - "model": "::", - "type": "", - "namespace": "", - "attributes": { - "" - }, - "depends_on": [] - } - ] +{ + "name": "", + "model": "::", + "type": "", + "namespace": "", + "attributes": { + "" + }, + "depends_on": [] +} ``` {{% /tab %}} {{< /tabs >}} +{{% /tab %}} +{{< /tabs >}} + The following properties are available for modular resources: | Name | Type | Required? | Description | | ---- | ---- | --------- | ----------- | +| `attributes` | object | **Required** | Any configuration attributes for your model Check the module's GitHub Readme for information about available configuration attributes for a resource. | | `name` | string | **Required** | What you want to name this instance of your modular resource. | | `namespace` | string | **Required** | The namespace of the API (the first part of the {{< glossary_tooltip term_id="api-namespace-triplet" text="API namespace triplet">}}). This will be `rdk` unless the module implements a [custom, non-standard API](/registry/advanced/). See [Valid API identifiers](/how-tos/create-module/#valid-api-identifiers). | | `type` | string | **Required** | The {{< glossary_tooltip term_id="subtype" text="subtype">}} of the API (the third part of the {{< glossary_tooltip term_id="api-namespace-triplet" text="API namespace triplet">}}). See [Valid API identifiers](/how-tos/create-module/#valid-api-identifiers). | | `model` | string | **Required** | The full {{< glossary_tooltip term_id="model-namespace-triplet" text="model namespace triplet">}} of the modular resource's {{< glossary_tooltip term_id="model" text="model" >}}. | | `depends_on` | array | Optional | The `name` of components you want to confirm are available on your machine alongside your modular resource. Often a [board](/components/board/). Unnecessary if you coded [implicit dependencies](/architecture/rdk/#dependency-management). | -{{% /tab %}} -{{< /tabs >}} - -All standard properties for configuration, such as `attributes` and `depends_on`, are also supported for modular resources. -The attributes available vary depending on your implementation. -If the module requires you to configure specific attributes, click the **Readme** link in the module's configuration card to view the specific attribute requirements on the module's GitHub page. - ### Module configuration {{< tabs >}} {{% tab name="Config Builder" %}} The following image shows an example of a configured module in a machine's config. -This ultrasonic sensor modular component in the previous section is provided by the [module](https://app.viam.com/module/viam/ultrasonic) shown here. +This ultrasonic sensor in the previous section is provided by the [`ultrasonic` module](https://app.viam.com/module/viam/ultrasonic) shown here. -{{}} +{{}} {{% /tab %}} {{% tab name="JSON" %}} @@ -210,7 +173,11 @@ The config of both a module and a corresponding modular resource resembles the f "type": "registry", "name": "_", "module_id": ":", - "version": "" + "version": "", + "env": { + "MY_VAR": "", + "PATH": ":${environment.PATH}" + } } ] } @@ -221,7 +188,7 @@ The config of both a module and a corresponding modular resource resembles the f The following is an example configuration for the [Intel Realsense module](https://app.viam.com/module/viam/realsense). The configuration adds `viam:camera:realsense` as a modular resource from the module `viam:realsense`. -The custom model is configured as a component with the name `myRealsenseCamera1`. +The model is configured as a component with the name `myRealsenseCamera1`. ```json {class="line-numbers linkable-line-numbers"} { @@ -259,21 +226,20 @@ The following properties are configurable for each module: | Name | Type | Required? | Description | | ---- | ---- | --------- | ----------- | -| `version` | string | **Required** |

You can specify:

  • a specific version (X.Y.Z) of the module to use
  • to pin the module version to the newest release, so your machine automatically updates to the latest version of the module that is available or to the latest patch release of a configured minor (X.Y.\_) or major (X.\_) version.

| +| `version` | string | **Required** |

You can specify:

  • a specific version (X.Y.Z) of the module to use
  • to pin the module version to the newest release, so your machine automatically updates to the latest version of the module that is available or to the latest patch release of a configured minor (X.Y.\_) or major (X.\_) version.
For more information, see [Module versioning](/registry/modular-resources/#module-versioning).

| | `type` | string | **Required** | `registry` or `local`, depending on whether the module is in the [Viam registry](https://app.viam.com/registry) or is only available [locally](/how-tos/create-module/#test-your-module-locally) on your computer. | | `name` | string | **Required** | The module author's organization namespace, followed by an underscore, followed by the name of the module. `_` | | `module_id` | string | **Required** | The module namespace, then a colon, then the name of the module. Identical to the first two pieces of the {{< glossary_tooltip term_id="model-namespace-triplet" text="model namespace triplet" >}} | +| `env` | object | **Optional** | Environment variables available to the module. For example `{ "API_KEY": "${environment.API_KEY}" }`. Some modules require that you set environment variables as part of configuration. Check the module's readme for more information. See [environments variables](#environment-variables). | -### Further configuration options - -{{< expand "Configure version update management" >}} +#### Module versioning You can configure how each module on your machine updates itself when a newer version becomes available from the Viam registry. By default, a newly-added module is set to pin to the specific patch release (**Patch (X.Y.Z)**) of the version you added, meaning that the module will _never automatically update itself_. To allow automatic module updates when a new version of the module becomes available in the Viam registry, set the **Pinned version type** for your module in its module card on the **CONFIGURE** tab. -{{}} +{{}} The following update options are available: @@ -296,33 +262,23 @@ For any version type other than **Patch (X.Y.Z)**, the module will upgrade as so If, for example, the module provides a motor component, and the motor is running, it will stop while the module upgrades. {{% /alert %}} -{{< /expand >}} -{{< expand "Use environment variables with a registry module" >}} - -Some modules require that you set specific environment variables as part of configuration. -You can click the **Readme** link in the upper-right corner of the module configuration card to view any specific requirements on the module's GitHub page. +#### Environment variables -Module environment variables can be either: +Each module has access to the following default environment variables: -- Static string values, or -- References to a system environment variable. + +| Name | Description | +| ---- | ----------- | +| `VIAM_HOME` | The root of the `viam-server` configuration.
Default: `$HOME/.viam` | +| `VIAM_MODULE_ROOT` | The root of the module install directory. The module process uses this directory as its current working directory (`cwd`). This variable is useful for file navigation that is relative to the root of the module. If you are using a [local module](/how-tos/create-module/#test-your-module-locally), you must set this value manually if your module requires it.
Example: `/opt/my-module/verxxxx-my-module/` | +| `VIAM_MODULE_DATA` | A persistent folder location a module can use to store data across reboots and versions. This location is a good place to store [python virtual environments](/sdks/python/python-venv/).
Example: `$VIAM_HOME/module-data/cloud-machine-id/my-module-name/` | +| `VIAM_MODULE_ID` | The module ID of the module.
Example: `viam:realsense` | -For example, if your module requires a `MODULE_USER` environment variable, you can add it with the following configuration: +You can also set additional environment variables. -```json {class="line-numbers linkable-line-numbers"} -{ - "modules": [ - { - ... - "env": { - "MODULE_USER": "my-username" - } - } - ] -} -``` +{{% expand "Example: string value" %}} -Or if you are using a module that requires access to an additional program or library on your machine, you can create a `PATH` environment variable for that module: +Set the environment variable `MODULE_USER`: ```json {class="line-numbers linkable-line-numbers"} { @@ -330,84 +286,53 @@ Or if you are using a module that requires access to an additional program or li { ... "env": { - "PATH": "/home/username/bin:${environment.PATH}" + "MODULE_USER": "my-username" } } ] } ``` -This configures a module environment variable `PATH` that uses your system's `PATH` (which you can view by running `echo $PATH`) as a base, and adds one additional filesystem path: /home/username/bin. +{{% /expand%}} -The notation `${environment.}` can be used to access any system environment variable that `viam-server` has access to, where `` represents a system environment variable, like `PATH`, `USER`, or `PWD`. +Use the notation `${environment.}` to access any system environment variable that `viam-server` has access to, where `` represents a system environment variable, like `PATH`, `USER`, or `PWD`. For example, you can use `${environment.HOME}` to access the `HOME` environment variable for the user running `viam-server`. -To configure a modular resource with an environment variable, navigate to the **CONFIGURE** tab on your machine's page in the Viam app, select **JSON** mode, and add the following `env` configuration to the `modules` section: - -{{< tabs >}} -{{% tab name="JSON Template" %}} - -```json {class="line-numbers linkable-line-numbers"} -{ - "modules": [ - { - "type": "registry", - "name": "", - "module_id": ":", - "version": "", - "env": { - "MY_VAR": "", - "PATH": ":${environment.PATH}" - } - } - ] -} -``` +{{% expand "Example: system variable" %}} -{{% /tab %}} -{{% tab name="JSON Example" %}} +To set the path to a program or library on a machine, you can set a system variable: ```json {class="line-numbers linkable-line-numbers"} { "modules": [ { - "type": "registry", - "name": "my-module", - "module_id": "my-namespace:my-module", - "version": "1.0.0", + ... "env": { - "PATH": "/home/username/bin:${environment.PATH}", - "MY_USER": "username" + "PATH": "/home/username/bin:${environment.PATH}" } } ] } ``` -{{% /tab %}} -{{< /tabs >}} - -To delete an environment variable configuration, delete the `env` section from your smart machine's configuration. - -### Default environment variables +{{% /expand%}} -When a module is instantiated, it has access to the following default environment variables: +## How modules run - -| Name | Description | -| ---- | ----------- | -| `VIAM_HOME` | The root of the `viam-server` configuration.
Default: `$HOME/.viam` | -| `VIAM_MODULE_ROOT` | The root of the module install directory. The module process uses this directory as its current working directory (`cwd`). This variable is useful for file navigation that is relative to the root of the module. If you are using a [local module](/how-tos/create-module/#test-your-module-locally), you must set this value manually if your module requires it.
Example: `/opt/my-module/verxxxx-my-module/` | -| `VIAM_MODULE_DATA` | A persistent folder location a module can use to store data across reboots and versions. This location is a good place to store [python virtual environments](/sdks/python/python-venv/).
Example: `$VIAM_HOME/module-data/cloud-machine-id/my-module-name/` | -| `VIAM_MODULE_ID` | The module ID of the module.
Example: `viam:realsense` | - -{{< /expand >}} +Modules run alongside [`viam-server`](/architecture/rdk/) as separate processes, communicating with `viam-server` over UNIX sockets. +When a module initializes, it registers its {{< glossary_tooltip term_id="model" text="model or models" >}} and associated [APIs](/appendix/apis/) with `viam-server`, making the new model available for use. +`viam-server` manages the [dependencies](/architecture/rdk/#dependency-management), [start-up](/architecture/rdk/#start-up), [reconfiguration](/architecture/rdk/#reconfiguration), [data management](/services/data/capture-sync/#configure-data-capture-and-sync), and [shutdown](/architecture/rdk/#shutdown) behavior of your modular resource. ## Next steps -Now that you've configured a modular resource, test it with the [**CONTROL** tab](/fleet/control/) and program it with the [Viam SDKs](/appendix/apis/). +You can write modules in a variety of programming languages, such as, Go, Python, C++, Rust, while implementing the respective [component APIs](/appendix/apis/components/) or [service APIs](/appendix/apis/services/). + +{{< cards >}} +{{% card link="/how-tos/sensor-module/" class="fit-contain" noimage=true %}} +{{% card link="/how-tos/create-module/" class="fit-contain" noimage=true %}} +{{< /cards >}} -You can also check out these tutorials that configure and use modular resources: +To see modular resources in actions, follow one of these tutorials: {{< cards >}} {{% card link="/tutorials/projects/make-a-plant-watering-robot/" %}} diff --git a/docs/services/ml/training-scripts.md b/docs/registry/training-scripts.md similarity index 79% rename from docs/services/ml/training-scripts.md rename to docs/registry/training-scripts.md index f13331550d..c6aa78f6e0 100644 --- a/docs/services/ml/training-scripts.md +++ b/docs/registry/training-scripts.md @@ -1,21 +1,26 @@ --- title: "Training scripts" linkTitle: "Training scripts" -weight: 10 +weight: 30 type: "docs" description: "The Viam registry hosts custom Python ML training scripts, which you can use to train machine learning models." no_list: true icon: true images: ["/services/icons/ml.svg"] modulescript: true -date: "2024-09-03" +aliases: + - /services/ml/training-scripts/ +date: "2024-10-20" # updated: "" # When the content was last entirely checked --- The Viam registry hosts custom Python ML training scripts, which you can use to train machine learning models. -You can upload your own training script by following the guide to [Create custom training scripts](/how-tos/create-custom-training-scripts/). -You can search the available ML training scripts from the Viam registry here: +{{< alert title="In this page" color="note" >}} +{{% toc %}} +{{< /alert >}} + +## Training scripts in the registry {{}} diff --git a/docs/services/data/dataset.md b/docs/services/data/dataset.md index 5f291efd76..3b26c600f9 100644 --- a/docs/services/data/dataset.md +++ b/docs/services/data/dataset.md @@ -24,7 +24,7 @@ You can create and manage datasets using the [**DATA** tab](https://app.viam.com Filtered datasets are views and not materialized. That means the data you are viewing may change as you label and train on the dataset. -Your dataset is also not versioned. If you train [ML models](/services/ml/ml-models/) on your dataset and the dataset changes existing models will not be affected but any new models you train will use the dataset with the data in it at the time of training. +Your dataset is also not versioned. If you train [ML models](/registry/ml-models/) on your dataset and the dataset changes existing models will not be affected but any new models you train will use the dataset with the data in it at the time of training. {{< /alert >}} ## Labels diff --git a/docs/services/ml/_index.md b/docs/services/ml/_index.md index 4297605af5..05067373e2 100644 --- a/docs/services/ml/_index.md +++ b/docs/services/ml/_index.md @@ -1,24 +1,27 @@ --- -title: "Machine Learning" -linkTitle: "Machine Learning" +title: "ML Model Service" +linkTitle: "ML Model" weight: 30 type: "docs" -tags: ["data management", "data", "services"] -no_list: true -description: "Use Viam's built-in machine learning capabilities to train image classification models and deploy these models to your machines." -images: ["/platform/ml.svg"] +tags: ["data management", "ml", "model training"] aliases: + - /manage/data/deploy-model/ + - /services/ml/ + - /ml/deploy/ + - /services/ml/deploy/ - /manage/ml/ - /ml/ +description: "Deploy machine learning models to a machine and use the vision service to detect or classify images or to create point clouds of identified objects." +modulescript: true +hide_children: true +icon: true +no_list: true +images: ["/platform/ml.svg"] date: "2024-09-03" # updated: "" # When the content was last entirely checked # SME: Aaron Casas --- -

-{{}} -

- Machine learning (ML) provides your machines with the ability to adjust their behavior based on models that recognize patterns or make predictions. Common use cases include: @@ -27,46 +30,58 @@ Common use cases include: - Object classification, which enables machines to separate people, animals, plants, or other objects into predefined categories based on their characteristics, and to perform different actions based on the classes of objects. - Speech recognition, natural language processing, and speech synthesis, which enable machines to verbally communicate with us. -Viam provides two services that together enable visual machine learning capabilities: the [ML model](/services/ml/deploy/) service and the [Computer Vision](/services/vision/) service. +The Machine Learning (ML) model service allows you to deploy [machine learning models](/registry/ml-models/) to your machine. +The service works with models trained inside and outside the Viam app: + +- You can [train](/how-tos/train-deploy-ml/) models on data from your machines. +- You can upload externally trained models on the [**MODELS** tab](https://app.viam.com/data/models) in the **DATA** section of the Viam app. +- You can use [ML models](https://app.viam.com/registry?type=ML+Model) from the [Viam Registry](https://app.viam.com/registry). +- You can use a [model](/registry/ml-models/) trained outside the Viam platform whose files are on your machine. + +## Configuration + +You must deploy an ML model service to use machine learning models on your machines. +Once you have deployed the ML model service, you can select an [ML model](#machine-learning-models-from-registry). + +After deploying your model, you need to configure an additional service to use the deployed model. +For example, you can configure an [`mlmodel` vision service](/services/vision/) to visualize the predictions your model makes. For other use cases, consider [creating custom functionality with a module](/how-tos/create-module/). -## Machine learning models +{{}} -Machine Learning (ML) models are mathematical models that can recognize patterns. -Currently Viam supports TensorFlow Lite, TensorFlow, ONNX, and PyTorch. +{{< alert title="Add support for other models" color="tip" >}} +ML models must be designed in particular shapes to work with the `mlmodel` [classification](/services/vision/mlmodel/) or [detection](/services/vision/mlmodel/) model of Viam's [vision service](/services/vision/). +See [ML Model Design](/registry/advanced/mlmodel-design/) to design modular ML model service with models that work with vision. +{{< /alert >}} -- You can upload externally trained models on the [**MODELS** tab](https://app.viam.com/data/models) in the **DATA** section of the Viam app. -- You can [train](/how-tos/train-deploy-ml/) models on data from your machines using different training scripts. -- You can use [ML models from the Viam Registry](https://app.viam.com/registry?type=ML+Model). -- You can use a [model](/services/ml/ml-models/) trained outside the Viam platform that's already available on your machine. +{{< alert title="Note" color="note" >}} +For some models of the ML model service, like the [Triton ML model service](https://github.com/viamrobotics/viam-mlmodelservice-triton/tree/main/) for Jetson boards, you can configure the service to use either the available CPU or a dedicated GPU. +{{< /alert >}} -For more information, see [ML Models](/services/ml/ml-models/) and [Training Scripts](/services/ml/training-scripts/). +## Machine learning models from registry -{{< cards >}} -{{% card link="/services/ml/ml-models/" noimage="True" %}} -{{% card link="/services/ml/training-scripts/" noimage="True" %}} -{{< /cards >}} +You can search the machine learning models that are available to deploy on this service from the registry here: + +{{}} -## ML Model service +## API -The [ML model service](/services/ml/deploy/) deploys and runs a machine learning model, such as a TensorFlow or ONNX model, on your machine and makes its output accessible to other services. -For example, the [Computer Vision](/services/vision/mlmodel/) `mlmodel` service, which can detect or classify objects, is built to work with the inferences from an ML model service. -As a detector, the service uses these inferences to interpret image data from images on your computer or a [camera](/components/camera/), drawing bounding boxes around objects. -As a classifier, the service returns class labels and confidence score based off the [inferences](/appendix/apis/services/ml/#infer) the underlying ML model makes from image data. +The [ML model service API](/appendix/apis/services/ml/) supports the following methods: + +{{< readfile "/static/include/services/apis/generated/mlmodel-table.md" >}} ## Next steps -For comprehensive guides on using data capture and synchronization together with the ML model service, see: +The ML model service only runs your model on the machine. +To use the inferences from the model, you must use an additional service such as a [vision service](/services/vision/): {{< cards >}} -{{% card link="/how-tos/image-data/" %}} -{{% card link="/how-tos/train-deploy-ml/" %}} -{{< /cards >}} +{{% manualcard link="/services/vision/mlmodel/" title="Create a visual detector or classifier" noimage="True" %}} -You can also follow one of these tutorials to see ML models in action: +Use your model deployed with the ML model service by adding a vision service that can provide detections or classifications depending on your ML model. + +{{% /manualcard %}} +{{% card link="/how-tos/train-deploy-ml/" noimage="True" %}} +{{% card link="/how-tos/detect-people/" customTitle="Detect people" noimage="true" %}} -{{< cards >}} -{{% card link="/tutorials/projects/helmet/" %}} -{{% card link="/tutorials/services/color-detection-scuttle/" %}} -{{% card link="/tutorials/projects/integrating-viam-with-openai/" customDescription="Add object detection, speech recognition, natural language processing, and speech synthesis capabilities to a machine." %}} {{< /cards >}} diff --git a/docs/services/ml/deploy/_index.md b/docs/services/ml/deploy/_index.md index ffefa01d07..0f68502803 100644 --- a/docs/services/ml/deploy/_index.md +++ b/docs/services/ml/deploy/_index.md @@ -19,7 +19,7 @@ date: "2024-09-03" # SME: Aaron Casas --- -The Machine Learning (ML) model service allows you to deploy [machine learning models](/services/ml/ml-models/) to your machine. +The Machine Learning (ML) model service allows you to deploy machine learning models to your machine. You can deploy: - a model you [trained](/how-tos/train-deploy-ml/) diff --git a/docs/services/ml/ml-models.md b/docs/services/ml/ml-models.md deleted file mode 100644 index e4ac3932e1..0000000000 --- a/docs/services/ml/ml-models.md +++ /dev/null @@ -1,94 +0,0 @@ ---- -title: "ML Models" -linkTitle: "ML Models" -weight: 40 -type: "docs" -tags: ["data management", "ml", "model training"] -images: ["/services/ml/train-model.gif"] -videos: ["/services/ml/train-model.webm","/services/ml/train-model.mp4"] -videoAlt: "Add a bounding box around the dog in an image." -aliases: - - /data/train-model/ -description: "Machine learning models are mathematical models that can recognize patterns. You can use them on your machines to interpret the machine's surroundings." -aliases: - - /services/ml/upload-model/ - - /services/ml/edit/ - - /ml/edit/ - - /manage/data/upload-model/ - - /manage/ml/upload-model/ - - /ml/upload-model/ -no_service: true -modulescript: true -# SME: Tahiya + Alexa Greenberg ---- - -Machine Learning (ML) models are mathematical models that can recognize patterns. - -The [ML model service](/services/ml/deploy/) runs ML models on your machines. -Services like the [vision service](/services/vision/mlmodel/) can then use the ML model services to provide your machine with information about its surroundings. -The ML model service works with models trained inside and outside the Viam app: - -- You can upload externally trained models on the [**MODELS** tab](https://app.viam.com/data/models) in the **DATA** section of the Viam app. -- You can [train](/how-tos/train-deploy-ml/) models on data from your machines. -- You can use [ML models](https://app.viam.com/registry?type=ML+Model) from the Viam Registry. -- You can use a [model](/services/ml/ml-models/) trained outside the Viam platform that's already available on your machine. - -## Available machine learning models in the registry - -You can search the machine learning models that are available to deploy on this service from the registry here: - -{{}} - -## Model framework support - -Viam currently supports the following frameworks: - - -| Model Framework | ML Model Service | Hardware Support | System Architecture | Description | -| --------------- | --------------- | ---------------- | ------------------- | ----------- | -| [TensorFlow Lite](https://www.tensorflow.org/lite) | [`tflite_cpu`](/services/ml/deploy/tflite_cpu/) | Any CPU
Nvidia GPU | Linux, Raspbian, MacOS, Android | Quantized version of TensorFlow that has reduced compatibility for models but supports more hardware. Uploaded models must adhere to the [model requirements](/services/ml/deploy/tflite_cpu/#model-requirements). | -| [ONNX](https://onnx.ai/) | [`onnx_cpu`](https://github.com/viam-labs/onnx-cpu) | Any CPU
Nvidia GPU | Android, MacOS, Linux arm-64 | Universal format that is not optimized for hardware inference but runs on a wide variety of machines. | -| [TensorFlow](https://www.tensorflow.org/) | [`triton`](https://github.com/viamrobotics/viam-mlmodelservice-triton) | Nvidia GPU | Linux (Jetson) | A full framework that is made for more production-ready systems. | -| [PyTorch](https://pytorch.org/) | [`triton`](https://github.com/viamrobotics/viam-mlmodelservice-triton) | Nvidia GPU | Linux (Jetson) | A full framework that was built primarily for research. Because of this, it is much faster to do iterative development with (model doesn’t have to be predefined) but it is not as “production ready” as TensorFlow. It is the most common framework for OSS models because it is the go-to framework for ML researchers. | - -## Versions - -If you [deploy a model](/services/ml/) to a machine, Viam automatically assumes that this is the `latest` version of the model and that you would always like to deploy the `latest` version of the model to the machine. -If you train a new version of that model, Viam will automatically deploy the new version to the machine and replace the old version. - -If you do not want Viam to automatically deploy the `latest` version of the model, you can change `packages` configuration in the [JSON machine configuration](/configure/#the-configure-tab). -The model package config looks like this: - -```json -{ - "package": "/", - "version": "YYYY-MM-DDThh-mm-ss", - "name": "", - "type": "ml_model" -} -``` - -You can get the version number from a specific model version by navigating to the [models page](https://app.viam.com/data/models) finding the model's row, clicking on the right-side menu marked with **_..._** and selecting **Copy package JSON**. For example: `2024-02-28T13-36-51`. - -{{< alert title="Note" color="note" >}} -When you [train](/how-tos/train-deploy-ml/) a new version of a model, the previous model remains unchanged and is not used as input. -{{< /alert >}} - -If you need to make changes to a model, you can edit or delete it on its page which you can access from the [**MODELS** tab](https://app.viam.com/data/models). - -## Next steps - -Use the ML model service to deploy a machine learning model to your machine: - -{{< cards >}} -{{% card link="/services/ml/deploy/" %}} -{{% card link="/how-tos/train-deploy-ml/" %}} -{{< /cards >}} - -Follow one of these tutorials to see ML models in action: - -{{< cards >}} -{{% card link="/tutorials/projects/helmet/" %}} -{{% card link="/tutorials/services/color-detection-scuttle/" %}} -{{% card link="/tutorials/projects/integrating-viam-with-openai/" customDescription="Add object detection, speech recognition, natural language processing, and speech synthesis capabilities to a machine." %}} -{{< /cards >}} diff --git a/docs/services/ml/deploy/tflite_cpu.md b/docs/services/ml/tflite_cpu.md similarity index 98% rename from docs/services/ml/deploy/tflite_cpu.md rename to docs/services/ml/tflite_cpu.md index d8c20cf9d7..cf7a401e02 100644 --- a/docs/services/ml/deploy/tflite_cpu.md +++ b/docs/services/ml/tflite_cpu.md @@ -21,7 +21,7 @@ To work with the `tflite_cpu` ML model service, an ML model is comprised of a }} diff --git a/docs/services/slam/cartographer/_index.md b/docs/services/slam/cartographer/_index.md index 7f78b27dc2..5b95d715b5 100644 --- a/docs/services/slam/cartographer/_index.md +++ b/docs/services/slam/cartographer/_index.md @@ -17,7 +17,6 @@ aliases: [The Cartographer Project](https://github.com/cartographer-project) contains a C++ library that performs dense Simultaneous Localization And Mapping (SLAM). To use Cartographer with the Viam {{< glossary_tooltip term_id="slam" text="SLAM" >}} service, you can use the [`cartographer`](https://app.viam.com/module/viam/cartographer) {{< glossary_tooltip term_id="modular-resource" text="modular resource" >}}. -See the [Use Modules](/registry/#use-modules) section for instructions on using a module from the Viam registry on your machine. The source code for this module is available on the [`viam-cartographer` GitHub repository](https://github.com/viamrobotics/viam-cartographer). diff --git a/docs/services/vision/mlmodel.md b/docs/services/vision/mlmodel.md index 1ea289eb71..9e327f13b1 100644 --- a/docs/services/vision/mlmodel.md +++ b/docs/services/vision/mlmodel.md @@ -27,14 +27,14 @@ Before configuring your `mlmodel` detector or classifier, you need to:

1. Train or upload an ML model

-You can add an [existing model](/services/ml/ml-models/) or [train your own models](/how-tos/train-deploy-ml/) for object detection and classification using data from the [data management service](/services/data/). +You can add an [existing model](/registry/ml-models/) or [train your own models](/how-tos/train-deploy-ml/) for object detection and classification using data from the [data management service](/services/data/). {{% /manualcard %}} {{% manualcard %}}

2. Deploy your ML model

-To use ML models with your machine, use a suitable [ML model service](/services/ml/deploy/) to deploy and run the model. +To use ML models with your machine, use a suitable [ML model service](/services/ml/) to deploy and run the model. {{% /manualcard %}} {{< /cards >}} @@ -123,7 +123,7 @@ The following attributes are available for an `mlmodel` detector or classifier: | Parameter | Type | Required? | Description | | --------- | ---- | --------- | ----------- | -| `mlmodel_name` | string | **Required** | The name of the [ML model service](/services/ml/deploy/) you want to use the model from. | +| `mlmodel_name` | string | **Required** | The name of the [ML model service](/services/ml/) you want to use the model from. | | `remap_output_names` | object | Optional | The names of your output tensors, mapped to the service requirements. See [Tensor names](#tensor-names) for more information. | | `remap_input_names` | object | Optional | The name of your input tensor, mapped to the service requirements. See [Tensor names](#tensor-names) for more information. | | `input_image_bgr` | bool | Optional | Set this to `true` if the ML model service expects the input image to have BGR pixels, rather than RGB pixels.
Default: `false` | diff --git a/docs/tutorials/custom/controlling-an-intermode-rover-canbus.md b/docs/tutorials/custom/controlling-an-intermode-rover-canbus.md index 6a11ac5400..2c31faa699 100644 --- a/docs/tutorials/custom/controlling-an-intermode-rover-canbus.md +++ b/docs/tutorials/custom/controlling-an-intermode-rover-canbus.md @@ -288,7 +288,7 @@ To run the modular resource, first copy the module binary to your Raspberry Pi. You will now configure your base in the [Viam app](https://app.viam.com). Go to the [machine you added during setup](#machine-setup). -To make your module accessible to `viam-server`, you must [add it as a local module](/registry/configure/#add-a-local-module). +To make your module accessible to `viam-server`, you must add it as a local module: 1. Navigate to the **CONFIGURE** tab of your machine's page in [the Viam app](https://app.viam.com). 1. Click the **+** (Create) icon next to your machine part in the left-hand menu and select **Local module**, then **Local module**. diff --git a/docs/tutorials/projects/verification-system.md b/docs/tutorials/projects/verification-system.md index 71a650ecdb..d19a066bea 100644 --- a/docs/tutorials/projects/verification-system.md +++ b/docs/tutorials/projects/verification-system.md @@ -169,7 +169,7 @@ Then, create a new dataset using your uploaded images and train a new model usin You only want this model to be able to distinguish between what is and isn't a person, so you can conduct this training step with anyone, not necessarily the specific people you intend to approve later. 3. [Train a model on your dataset](/how-tos/train-deploy-ml/). Give it the name `"persondetect"`, and select **Object Detection** as the **Model Type**. -4. [Deploy the model](/services/ml/deploy/) to your machine so it can be used by other services, such as the vision service. +4. [Deploy the model](/services/ml/) to your machine so it can be used by other services, such as the vision service. Finally, configure an `mlmodel` detector to use your new `"persondetect"` ML model: diff --git a/layouts/shortcodes/modular-resources.html b/layouts/shortcodes/modular-resources.html index 76992ad174..eee40ab201 100644 --- a/layouts/shortcodes/modular-resources.html +++ b/layouts/shortcodes/modular-resources.html @@ -1,4 +1,4 @@ -

Search for additional {{.Get "type" }} models that you can add from the Viam Registry: +

Search for additional {{.Get "type" }} models that you can add from the Viam Registry:

For configuration information, click on the model name: