<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom"><channel><title>Concepts on Grafana Labs</title><link>https://grafana.com/docs/agent/v0.33/flow/concepts/</link><description>Recent content in Concepts on Grafana Labs</description><generator>Hugo -- gohugo.io</generator><language>en</language><atom:link href="/docs/agent/v0.33/flow/concepts/index.xml" rel="self" type="application/rss+xml"/><item><title>Components</title><link>https://grafana.com/docs/agent/v0.33/flow/concepts/components/</link><pubDate>Tue, 25 Apr 2023 17:26:25 +0000</pubDate><guid>https://grafana.com/docs/agent/v0.33/flow/concepts/components/</guid><content><![CDATA[&lt;h1 id=&#34;components&#34;&gt;Components&lt;/h1&gt;
&lt;p&gt;&lt;em&gt;Components&lt;/em&gt; are the building blocks of Grafana Agent Flow. Each component is
responsible for handling a single task, such as retrieving secrets or
collecting Prometheus metrics.&lt;/p&gt;
&lt;p&gt;Components are composed of two parts:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Arguments: settings which configure a component.&lt;/li&gt;
&lt;li&gt;Exports: named values which a component exposes to other components.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Each component has a name which describes what that component is responsible
for. For example, the &lt;code&gt;local.file&lt;/code&gt; component is responsible for retrieving the
contents of files on disk.&lt;/p&gt;
&lt;p&gt;Components are specified in the config file by first providing the component&amp;rsquo;s
name with a user-specified label, and then by providing arguments to configure
the component:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;discovery.kubernetes &amp;#34;pods&amp;#34; {
  role = &amp;#34;pod&amp;#34;
}

discovery.kubernetes &amp;#34;nodes&amp;#34; {
  role = &amp;#34;node&amp;#34;
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;blockquote&gt;
&lt;p&gt;Components are referenced by combining the component name with its label. For
example, a &lt;code&gt;local.file&lt;/code&gt; component labeled &lt;code&gt;foo&lt;/code&gt; would be referenced as
&lt;code&gt;local.file.foo&lt;/code&gt;.&lt;/p&gt;
&lt;p&gt;The combination of a component&amp;rsquo;s name and its label must be unique within the
configuration file. This means multiple instances of a component may be
defined as long as each instance has a different label value.&lt;/p&gt;&lt;/blockquote&gt;
&lt;h2 id=&#34;pipelines&#34;&gt;Pipelines&lt;/h2&gt;
&lt;p&gt;Most arguments for a component in a config file are constant values, such
setting a &lt;code&gt;log_level&lt;/code&gt; attribute to the quoted string &lt;code&gt;&amp;quot;debug&amp;quot;&lt;/code&gt;:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;log_level = &amp;#34;debug&amp;#34;&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;&lt;em&gt;Expressions&lt;/em&gt; can be used to dynamically compute the value of an argument at
runtime. Among other things, expressions can be used to retrieve the value of
an environment variable (&lt;code&gt;log_level = env(&amp;quot;LOG_LEVEL&amp;quot;)&lt;/code&gt;) or to reference an
exported field of another component (&lt;code&gt;log_level = local.file.log_level.content&lt;/code&gt;).&lt;/p&gt;
&lt;p&gt;When a component&amp;rsquo;s argument references an exported field of another component,
a dependant relationship is created: a component&amp;rsquo;s input (arguments) now
depends on another component&amp;rsquo;s output (exports). The input of the component
will now be re-evaluated any time the exports of the components it references
get updated.&lt;/p&gt;
&lt;p&gt;The flow of data through the set of references between components forms a
&lt;em&gt;pipeline&lt;/em&gt;.&lt;/p&gt;
&lt;p&gt;An example pipeline may look like this:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;A &lt;code&gt;local.file&lt;/code&gt; component watches a file on disk containing an API key.&lt;/li&gt;
&lt;li&gt;A &lt;code&gt;prometheus.remote_write&lt;/code&gt; component is configured to receive metrics and
forward them to an external database using the API key from the &lt;code&gt;local.file&lt;/code&gt;
for authentication.&lt;/li&gt;
&lt;li&gt;A &lt;code&gt;discovery.kubernetes&lt;/code&gt; component discovers and exports Kubernetes Pods
where metrics can be collected.&lt;/li&gt;
&lt;li&gt;A &lt;code&gt;prometheus.scrape&lt;/code&gt; component references the exports of the previous
component, and sends collected metrics to the &lt;code&gt;prometheus.remote_write&lt;/code&gt;
component.&lt;/li&gt;
&lt;/ol&gt;
&lt;p align=&#34;center&#34;&gt;
&lt;img src=&#34;../../../assets/concepts_example_pipeline.svg&#34; alt=&#34;Flow of example pipeline&#34; width=&#34;500&#34; /&gt;
&lt;/p&gt;
&lt;p&gt;The following config file represents the above pipeline:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;// Get our API key from disk.
//
// This component has an exported field called &amp;#34;content&amp;#34;, holding the content
// of the file.
//
// local.file.api_key will watch the file and update its exports any time the
// file changes.
local.file &amp;#34;api_key&amp;#34; {
  filename  = &amp;#34;/var/data/secrets/api-key&amp;#34;

  // Mark this file as sensitive to prevent its value from being shown in the
  // UI.
  is_secret = true
}

// Create a prometheus.remote_write component which other components can send
// metrics to.
//
// This component exports a &amp;#34;receiver&amp;#34; value which can be used by other
// components to send metrics.
prometheus.remote_write &amp;#34;prod&amp;#34; {
  endpoint {
    url = &amp;#34;https://prod:9090/api/v1/write&amp;#34;

    basic_auth {
      username = &amp;#34;admin&amp;#34;

      // Use our password file for authenticating with the production database.
      password = local.file.api_key.content
    }
  }
}

// Find Kubernetes pods where we can collect metrics.
//
// This component exports a &amp;#34;targets&amp;#34; value which contains the list of
// discovered pods.
discovery.kubernetes &amp;#34;pods&amp;#34; {
  role = &amp;#34;pod&amp;#34;
}

// Collect metrics from Kubernetes pods and send them to prod.
prometheus.scrape &amp;#34;default&amp;#34; {
  targets    = discovery.kubernetes.pods.targets
  forward_to = [prometheus.remote_write.prod.receiver]
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
]]></content><description>&lt;h1 id="components">Components&lt;/h1>
&lt;p>&lt;em>Components&lt;/em> are the building blocks of Grafana Agent Flow. Each component is
responsible for handling a single task, such as retrieving secrets or
collecting Prometheus metrics.&lt;/p></description></item><item><title>Component controller</title><link>https://grafana.com/docs/agent/v0.33/flow/concepts/component_controller/</link><pubDate>Wed, 12 Mar 2025 11:45:31 +0100</pubDate><guid>https://grafana.com/docs/agent/v0.33/flow/concepts/component_controller/</guid><content><![CDATA[&lt;h1 id=&#34;component-controller&#34;&gt;Component controller&lt;/h1&gt;
&lt;p&gt;The &lt;em&gt;component controller&lt;/em&gt; is the core part of Grafana Agent Flow which manages
components at runtime.&lt;/p&gt;
&lt;p&gt;It is responsible for:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Reading and validating the config file.&lt;/li&gt;
&lt;li&gt;Managing the lifecycle of defined components.&lt;/li&gt;
&lt;li&gt;Evaluating the arguments used to configure components.&lt;/li&gt;
&lt;li&gt;Reporting the health of defined components.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;component-graph&#34;&gt;Component graph&lt;/h2&gt;
&lt;p&gt;As discussed in &lt;a href=&#34;../components/&#34;&gt;Components&lt;/a&gt;, a relationship between components is created
when an expression is used to set the argument of one component to an exported
field of another component.&lt;/p&gt;
&lt;p&gt;The set of all components and the relationships between them define a &lt;a href=&#34;https://en.wikipedia.org/wiki/Directed_acyclic_graph&#34; target=&#34;_blank&#34; rel=&#34;noopener noreferrer&#34;&gt;directed
acyclic graph&lt;/a&gt; (DAG), which informs the component controller which
references are valid and in what order components must be evaluated.&lt;/p&gt;
&lt;p&gt;For a config file to be valid, components must not reference themselves or
contain a cyclic reference:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;// INVALID: local.file.some_file can not reference itself:
local.file &amp;#34;self_reference&amp;#34; {
  filename = local.file.self_reference.content
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;// INVALID: cyclic reference between local.file.a and local.file.b:
local.file &amp;#34;a&amp;#34; {
  filename = local.file.b.content
}
local.file &amp;#34;b&amp;#34; {
  filename = local.file.a.content
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;h2 id=&#34;component-evaluation&#34;&gt;Component evaluation&lt;/h2&gt;
&lt;p&gt;A component is &lt;em&gt;evaluated&lt;/em&gt; when its expressions are computed into concrete
values. The computed values are then used to configure the component&amp;rsquo;s runtime
behavior. The component controller is finished loading once all components are
evaluated, configured, and running.&lt;/p&gt;
&lt;p&gt;The component controller only evaluates a given component after evaluating all
of that component&amp;rsquo;s dependencies. Component that do not depend on other
components can be evaluated at any time during the evaluation process.&lt;/p&gt;
&lt;h2 id=&#34;component-reevaluation&#34;&gt;Component reevaluation&lt;/h2&gt;
&lt;p&gt;As mentioned in &lt;a href=&#34;../components/&#34;&gt;Components&lt;/a&gt;, a component is dynamic: a component can update
its exports any number of times throughout its lifetime.&lt;/p&gt;
&lt;p&gt;When a component updates its exports, a &lt;em&gt;controller reevaluation&lt;/em&gt; is triggered:
the component controller reevaluates any component which references the changed
component, any components which reference those components, and so on, until
all affected components are reevaluated.&lt;/p&gt;
&lt;h2 id=&#34;component-health&#34;&gt;Component health&lt;/h2&gt;
&lt;p&gt;At any given time, a component can have one of the following health states:&lt;/p&gt;
&lt;ol&gt;
&lt;li&gt;Unknown: default state, the component isn&amp;rsquo;t running yet.&lt;/li&gt;
&lt;li&gt;Healthy: the component is working as expected.&lt;/li&gt;
&lt;li&gt;Unhealthy: the component is not working as expected.&lt;/li&gt;
&lt;li&gt;Exited: the component has stopped and is no longer running.&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;By default, the component controller determines the health of a component. The
component controller marks a component as healthy as long as that component is
running and its most recent evaluation succeeded.&lt;/p&gt;
&lt;p&gt;Some components can report their own component-specific health information. For
example, the &lt;code&gt;local.file&lt;/code&gt; component reports itself as unhealthy if the file it
was watching gets deleted.&lt;/p&gt;
&lt;p&gt;The overall health of a component is determined by combining the
controller-reported health of the component with the component-specific health
information.&lt;/p&gt;
&lt;p&gt;An individual component&amp;rsquo;s health is independent of the health of any other
components it references: a component can be marked as healthy even if it
references an exported field of an unhealthy component.&lt;/p&gt;
&lt;h2 id=&#34;handling-evaluation-failures&#34;&gt;Handling evaluation failures&lt;/h2&gt;
&lt;p&gt;When a component fails to evaluate, it is marked as unhealthy with the reason
for why the evaluation failed.&lt;/p&gt;
&lt;p&gt;When an evaluation fails, the component continue operating as normal: it
continues using its previous set of evaluated arguments, and it can continue
exporting new values.&lt;/p&gt;
&lt;p&gt;This prevents failure propagation: if your &lt;code&gt;local.file&lt;/code&gt; component which watches
API keys suddenly stops working, other components continues using the last
valid API key until the component returns to a healthy state.&lt;/p&gt;
&lt;h2 id=&#34;updating-the-config-file&#34;&gt;Updating the config file&lt;/h2&gt;
&lt;p&gt;Both the &lt;code&gt;/-/reload&lt;/code&gt; HTTP endpoint and the &lt;code&gt;SIGHUP&lt;/code&gt; signal can be used to
inform the component controller to reload the config file. When this happens,
the component controller will synchronize the set of running components with
the ones in the config file, removing components which are no longer defined in
the config file and creating new components which were added to the config
file. All components managed by the controller will be reevaluated after
reloading.&lt;/p&gt;
]]></content><description>&lt;h1 id="component-controller">Component controller&lt;/h1>
&lt;p>The &lt;em>component controller&lt;/em> is the core part of Grafana Agent Flow which manages
components at runtime.&lt;/p>
&lt;p>It is responsible for:&lt;/p>
&lt;ul>
&lt;li>Reading and validating the config file.&lt;/li>
&lt;li>Managing the lifecycle of defined components.&lt;/li>
&lt;li>Evaluating the arguments used to configure components.&lt;/li>
&lt;li>Reporting the health of defined components.&lt;/li>
&lt;/ul>
&lt;h2 id="component-graph">Component graph&lt;/h2>
&lt;p>As discussed in &lt;a href="../components/">Components&lt;/a>, a relationship between components is created
when an expression is used to set the argument of one component to an exported
field of another component.&lt;/p></description></item><item><title>Modules</title><link>https://grafana.com/docs/agent/v0.33/flow/concepts/modules/</link><pubDate>Wed, 12 Mar 2025 11:45:31 +0100</pubDate><guid>https://grafana.com/docs/agent/v0.33/flow/concepts/modules/</guid><content><![CDATA[&lt;h1 id=&#34;modules&#34;&gt;Modules&lt;/h1&gt;
&lt;p&gt;&lt;em&gt;Modules&lt;/em&gt; are a way to create Grafana Agent Flow configurations which can be
loaded as a component. Modules are a great way to parameterize a configuration
to create reusable pipelines.&lt;/p&gt;
&lt;p&gt;Modules are Grafana Agent Flow configurations which have:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Arguments: settings which configure a module.&lt;/li&gt;
&lt;li&gt;Exports: named values which a module exposes to the consumer of the module.&lt;/li&gt;
&lt;li&gt;Components: Grafana Agent Flow Components to run when the module is running.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Modules are loaded into Grafana Agent Flow by using a &lt;a href=&#34;#module-loaders&#34;&gt;Module
loader&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Refer to the documentation for the &lt;a href=&#34;../../reference/config-blocks/argument/&#34;&gt;argument block&lt;/a&gt; and &lt;a href=&#34;../../reference/config-blocks/export/&#34;&gt;export block&lt;/a&gt; to
learn how to define arguments and exports for a module.&lt;/p&gt;
&lt;h2 id=&#34;module-loaders&#34;&gt;Module loaders&lt;/h2&gt;
&lt;p&gt;A &lt;em&gt;Module loader&lt;/em&gt; is a Grafana Agent Flow component which retrieves a module
and runs the components defined inside of it.&lt;/p&gt;
&lt;p&gt;Module loader components are responsible for:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Retrieving the module source to run.&lt;/li&gt;
&lt;li&gt;Creating a &lt;a href=&#34;../component_controller/&#34;&gt;Component controller&lt;/a&gt; for the module to run in.&lt;/li&gt;
&lt;li&gt;Passing arguments to the loaded module.&lt;/li&gt;
&lt;li&gt;Exposing exports from the loaded module.&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Module loaders typically are called &lt;code&gt;module.LOADER_NAME&lt;/code&gt;. The list of module
loader components can be found in the list of Grafana Agent Flow
&lt;a href=&#34;../../reference/components/&#34;&gt;Components&lt;/a&gt;.&lt;/p&gt;
&lt;p&gt;Some module loaders may not support running modules with arguments or exports;
refer to the documentation for the module loader you are using for more
information.&lt;/p&gt;
&lt;h2 id=&#34;module-sources&#34;&gt;Module sources&lt;/h2&gt;
&lt;p&gt;Modules are designed to be flexible, and can have their configuration retrieved
from anywhere, such as:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;The local filesystem&lt;/li&gt;
&lt;li&gt;An S3 bucket&lt;/li&gt;
&lt;li&gt;An HTTP endpoint&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Each module loader component will support different ways of retrieving module
sources. The most generic module loader component, &lt;code&gt;module.string&lt;/code&gt;, can load
modules from the export of another Flow component:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;local.file &amp;#34;my_module&amp;#34; {
  filename = &amp;#34;PATH_TO_MODULE&amp;#34;
}

module.string &amp;#34;my_module&amp;#34; {
  content = local.file.my_module.content

  arguments {
    MODULE_ARGUMENT_NAME_1 = MODULE_ARGUMENT_VALUE_1
    MODULE_ARGUMENT_NAME_2 = MODULE_ARGUMENT_VALUE_2
    // ...
  }
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;h2 id=&#34;example-module&#34;&gt;Example module&lt;/h2&gt;
&lt;p&gt;This example module manages a pipeline which filters out debug- and info-level
log lines which are given to it:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;// argument.write_to is a required argument which specifies where filtered
// log lines should be sent.
//
// The value of the argument can be retrieved in this file with
// argument.write_to.value.
argument &amp;#34;write_to&amp;#34; {
  optional = false
}

// loki.process.filter is our component which executes the filtering, passing
// filtered logs to argument.write_to.value.
loki.process &amp;#34;filter&amp;#34; {
  // Drop all debug- and info-level logs.
  stage.match {
    selector = &amp;#34;{job!=\&amp;#34;\&amp;#34;} |~ \&amp;#34;level=(debug|info)\&amp;#34;&amp;#34;
    action   = &amp;#34;drop&amp;#34;
  }

  // Send processed logs to our argument.
  forward_to = argument.write_to.value
}

// export.filter_input exports a value to the consumer of the module.
export &amp;#34;filter_input&amp;#34; {
  // Expose the receiver of loki.process so the module consumer can send
  // logs to our loki.process component.
  value = loki.process.filter.receiver
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;It can then be used as a processing step before writing logs to Loki:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;loki.source.file &amp;#34;self&amp;#34; {
  targets = LOG_TARGETS

  // Forward collected logs to the input of our filter.
  forward_to = [module.string.filter.exports.logs_input]
}

module.file &amp;#34;log_filter&amp;#34; {
  filename = &amp;#34;/path/to/modules/log_filter.river&amp;#34;

  arguments {
    // Configure the filter to forward filtered logs to loki.echo below.
    logs_output = [loki.write.default.receiver],
  }
}

loki.write &amp;#34;default&amp;#34; {
  endpoint {
    url = &amp;#34;LOKI_URL&amp;#34;
  }
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
]]></content><description>&lt;h1 id="modules">Modules&lt;/h1>
&lt;p>&lt;em>Modules&lt;/em> are a way to create Grafana Agent Flow configurations which can be
loaded as a component. Modules are a great way to parameterize a configuration
to create reusable pipelines.&lt;/p></description></item><item><title>Configuration language</title><link>https://grafana.com/docs/agent/v0.33/flow/concepts/configuration_language/</link><pubDate>Wed, 12 Mar 2025 11:45:31 +0100</pubDate><guid>https://grafana.com/docs/agent/v0.33/flow/concepts/configuration_language/</guid><content><![CDATA[&lt;h1 id=&#34;configuration-language&#34;&gt;Configuration language&lt;/h1&gt;
&lt;p&gt;The Grafana Agent Flow &lt;em&gt;configuration language&lt;/em&gt; refers to the language used in
configuration files which define and configure components to run.&lt;/p&gt;
&lt;p&gt;The configuration language is called River, a Terraform/HCL-inspired language:&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;prometheus.scrape &amp;#34;default&amp;#34; {
  targets = [{
    &amp;#34;__address__&amp;#34; = &amp;#34;demo.robustperception.io:9090&amp;#34;,
  }]
  forward_to = [prometheus.remote_write.default.receiver]
}

prometheus.remote_write &amp;#34;default&amp;#34; {
  endpoint {
    url = &amp;#34;http://localhost:9009/api/prom/push&amp;#34;
  }
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;River was designed with the following requirements in mind:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;&lt;em&gt;Fast&lt;/em&gt;: The configuration language must be fast so the component controller
can evaluate changes as quickly as possible.&lt;/li&gt;
&lt;li&gt;&lt;em&gt;Simple&lt;/em&gt;: The configuration language must be easy to read and write to
minimize the learning curve.&lt;/li&gt;
&lt;li&gt;&lt;em&gt;Debuggable&lt;/em&gt;: The configuration language must give detailed information when
there&amp;rsquo;s a mistake in the config file.&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;attributes&#34;&gt;Attributes&lt;/h2&gt;
&lt;p&gt;&lt;em&gt;Attributes&lt;/em&gt; are used to configure individual settings. They always take the
form of &lt;code&gt;ATTRIBUTE_NAME = ATTRIBUTE_VALUE&lt;/code&gt;.&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;log_level = &amp;#34;debug&amp;#34;&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;This sets the &lt;code&gt;log_level&lt;/code&gt; attribute to &lt;code&gt;&amp;quot;debug&amp;quot;&lt;/code&gt;.&lt;/p&gt;
&lt;h2 id=&#34;expressions&#34;&gt;Expressions&lt;/h2&gt;
&lt;p&gt;Expressions are used to compute the value of an attribute. The simplest
expressions are constant values like &lt;code&gt;&amp;quot;debug&amp;quot;&lt;/code&gt;, &lt;code&gt;32&lt;/code&gt;, or &lt;code&gt;[1, 2, 3, 4]&lt;/code&gt;. River
supports more complex expressions, such as:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;Referencing the exports of components: &lt;code&gt;local.file.password_file.content&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;Mathematical operations: &lt;code&gt;1 &#43; 2&lt;/code&gt;, &lt;code&gt;3 * 4&lt;/code&gt;, &lt;code&gt;(5 * 6) &#43; (7 &#43; 8)&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;Equality checks: &lt;code&gt;local.file.file_a.content == local.file.file_b.content&lt;/code&gt;&lt;/li&gt;
&lt;li&gt;Calling functions from River&amp;rsquo;s standard library: &lt;code&gt;env(&amp;quot;HOME&amp;quot;)&lt;/code&gt; (retrieve the
value of the &lt;code&gt;HOME&lt;/code&gt; environment variable)&lt;/li&gt;
&lt;/ul&gt;
&lt;p&gt;Expressions may be used for any attribute inside a component definition.&lt;/p&gt;
&lt;h3 id=&#34;referencing-component-exports&#34;&gt;Referencing component exports&lt;/h3&gt;
&lt;p&gt;The most common expression is to reference the exports of a component like
&lt;code&gt;local.file.password_file.content&lt;/code&gt;. A reference to a component&amp;rsquo;s exports is
formed by merging the component&amp;rsquo;s name (e.g., &lt;code&gt;local.file&lt;/code&gt;), label (e.g.,
&lt;code&gt;password_file&lt;/code&gt;), and export name (e.g., &lt;code&gt;content&lt;/code&gt;), delimited by period.&lt;/p&gt;
&lt;p&gt;For components that don&amp;rsquo;t use labels, like
&lt;code&gt;prometheus.exporter.unix&lt;/code&gt;, only combine the component name with
export name: &lt;code&gt;prometheus.exporter.unix.targets&lt;/code&gt;.&lt;/p&gt;
&lt;h2 id=&#34;blocks&#34;&gt;Blocks&lt;/h2&gt;
&lt;p&gt;&lt;em&gt;Blocks&lt;/em&gt; are used to configure components and groups of attributes. Each block
can contain any number of attributes or nested blocks.&lt;/p&gt;

&lt;div class=&#34;code-snippet &#34;&gt;&lt;div class=&#34;lang-toolbar&#34;&gt;
    &lt;span class=&#34;lang-toolbar__item lang-toolbar__item-active&#34;&gt;Alloy&lt;/span&gt;
    &lt;span class=&#34;code-clipboard&#34;&gt;
      &lt;button x-data=&#34;app_code_snippet()&#34; x-init=&#34;init()&#34; @click=&#34;copy()&#34;&gt;
        &lt;img class=&#34;code-clipboard__icon&#34; src=&#34;/media/images/icons/icon-copy-small-2.svg&#34; alt=&#34;Copy code to clipboard&#34; width=&#34;14&#34; height=&#34;13&#34;&gt;
        &lt;span&gt;Copy&lt;/span&gt;
      &lt;/button&gt;
    &lt;/span&gt;
    &lt;div class=&#34;lang-toolbar__border&#34;&gt;&lt;/div&gt;
  &lt;/div&gt;&lt;div class=&#34;code-snippet &#34;&gt;
    &lt;pre data-expanded=&#34;false&#34;&gt;&lt;code class=&#34;language-alloy&#34;&gt;prometheus.remote_write &amp;#34;default&amp;#34; {
  endpoint {
    url = &amp;#34;http://localhost:9009/api/prom/push&amp;#34;
  }
}&lt;/code&gt;&lt;/pre&gt;
  &lt;/div&gt;
&lt;/div&gt;
&lt;p&gt;This file has two blocks:&lt;/p&gt;
&lt;ul&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;prometheus.remote_write &amp;quot;default&amp;quot;&lt;/code&gt;: A labeled block which instantiates a
&lt;code&gt;prometheus.remote_write&lt;/code&gt; component. The label is the string &lt;code&gt;&amp;quot;default&amp;quot;&lt;/code&gt;.&lt;/p&gt;
&lt;/li&gt;
&lt;li&gt;
&lt;p&gt;&lt;code&gt;endpoint&lt;/code&gt;: An unlabeled block inside the component which configures an
endpoint to send metrics to. This block sets the &lt;code&gt;url&lt;/code&gt; attribute to specify
what the endpoint is.&lt;/p&gt;
&lt;/li&gt;
&lt;/ul&gt;
&lt;h2 id=&#34;more-information&#34;&gt;More information&lt;/h2&gt;
&lt;p&gt;River is documented in detail in &lt;a href=&#34;../../config-language/&#34;&gt;Configuration language&lt;/a&gt; section
of the Grafana Agent Flow docs.&lt;/p&gt;
]]></content><description>&lt;h1 id="configuration-language">Configuration language&lt;/h1>
&lt;p>The Grafana Agent Flow &lt;em>configuration language&lt;/em> refers to the language used in
configuration files which define and configure components to run.&lt;/p>
&lt;p>The configuration language is called River, a Terraform/HCL-inspired language:&lt;/p></description></item></channel></rss>