Skip to content

Commit 067dc3b

Browse files
committed
feat(api): add Pipe dependencies
Add the possibility to add any dependency. Useful, for instance, for external JDBC driver
1 parent 4ba0f98 commit 067dc3b

File tree

13 files changed

+124
-47
lines changed

13 files changed

+124
-47
lines changed

docs/modules/ROOT/partials/apis/camel-k-crds.adoc

Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4814,6 +4814,13 @@ string
48144814
48154815
Custom SA to use for the Pipe
48164816
4817+
|`dependencies` +
4818+
[]string
4819+
|
4820+
4821+
4822+
the list of Camel or Maven dependencies required by the Pipe
4823+
48174824
48184825
|===
48194826

e2e/common/traits/health_test.go

Lines changed: 10 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -29,11 +29,10 @@ import (
2929
"testing"
3030
"time"
3131

32-
"github.com/onsi/gomega/gstruct"
33-
3432
camelv1 "github.com/apache/camel-k/v2/pkg/apis/camel/v1"
3533

3634
. "github.com/onsi/gomega"
35+
"github.com/onsi/gomega/gstruct"
3736

3837
corev1 "k8s.io/api/core/v1"
3938

@@ -44,6 +43,7 @@ import (
4443
func TestHealthTrait(t *testing.T) {
4544
t.Parallel()
4645
WithNewTestNamespace(t, func(ctx context.Context, g *WithT, ns string) {
46+
4747
t.Run("Readiness condition with stopped route scaled", func(t *testing.T) {
4848
name := RandomizedSuffixName("java")
4949
g.Expect(KamelRun(t, ctx, ns, "files/Java.java",
@@ -240,12 +240,13 @@ func TestHealthTrait(t *testing.T) {
240240
g.Expect(CreateTimerKamelet(t, ctx, ns, source)()).To(Succeed())
241241
g.Expect(CreateLogKamelet(t, ctx, ns, sink)()).To(Succeed())
242242

243-
g.Expect(KamelBind(t, ctx, ns, source, sink, "-p",
244-
"source.message=Magicstring!", "-p", "sink.loggerName=binding",
245-
"--trait", "health.enabled=true",
246-
"--trait", "jolokia.enabled=true",
247-
"--trait", "jolokia.use-ssl-client-authentication=false",
248-
"--trait", "jolokia.protocol=http",
243+
g.Expect(KamelBind(t, ctx, ns, source, sink,
244+
"-p", "source.message=Magicstring!",
245+
"-p", "sink.loggerName=binding",
246+
"-t", "health.enabled=true",
247+
"-t", "jvm.agents=jolokia;https://repo1.maven.org/maven2/org/jolokia/jolokia-agent-jvm/2.3.0/jolokia-agent-jvm-2.3.0-javaagent.jar;host=*",
248+
"-t", "container.ports=jolokia;8778",
249+
"-d", "camel:management",
249250
"--name", name).Execute()).To(Succeed())
250251

251252
g.Eventually(IntegrationPodPhase(t, ctx, ns, name), TestTimeoutLong).Should(Equal(corev1.PodRunning))
@@ -470,5 +471,6 @@ func TestHealthTrait(t *testing.T) {
470471
WithTransform(IntegrationConditionReason, Equal(v1.IntegrationConditionDeploymentReadyReason)),
471472
WithTransform(IntegrationConditionMessage, Equal("1/1 ready replicas"))))
472473
})
474+
473475
})
474476
}

helm/camel-k/crds/camel-k-crds.yaml

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -24110,6 +24110,12 @@ spec:
2411024110
spec:
2411124111
description: the specification of a Pipe
2411224112
properties:
24113+
dependencies:
24114+
description: the list of Camel or Maven dependencies required by the
24115+
Pipe
24116+
items:
24117+
type: string
24118+
type: array
2411324119
errorHandler:
2411424120
description: ErrorHandler is an optional handler called upon an error
2411524121
occurring in the integration

pkg/apis/camel/v1/pipe_types.go

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -60,6 +60,8 @@ type PipeSpec struct {
6060
Replicas *int32 `json:"replicas,omitempty"`
6161
// Custom SA to use for the Pipe
6262
ServiceAccountName string `json:"serviceAccountName,omitempty"`
63+
// the list of Camel or Maven dependencies required by the Pipe
64+
Dependencies []string `json:"dependencies,omitempty"`
6365
}
6466

6567
// Endpoint represents a source/sink external entity (could be any Kubernetes resource or Camel URI).

pkg/apis/camel/v1/zz_generated.deepcopy.go

Lines changed: 5 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

pkg/client/camel/applyconfiguration/camel/v1/pipespec.go

Lines changed: 11 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

pkg/cmd/bind.go

Lines changed: 19 additions & 13 deletions
Original file line numberDiff line numberDiff line change
@@ -65,6 +65,7 @@ func newCmdBind(rootCmdOptions *RootCmdOptions) (*cobra.Command, *bindCmdOptions
6565
cmd.Flags().StringArray("annotation", nil, "Add an annotation to the Pipe. E.g. \"--annotation my.company=hello\"")
6666
cmd.Flags().Bool("force", false, "Force creation of Pipe regardless of potential misconfiguration.")
6767
cmd.Flags().String("service-account", "", "The SA to use to run this binding")
68+
cmd.Flags().StringArrayP("dependency", "d", nil, `A dependency that should be included, e.g., "camel:mail" for a Camel component, "mvn:org.my:app:1.0" for a Maven dependency`)
6869

6970
return &cmd, &options
7071
}
@@ -89,6 +90,7 @@ type bindCmdOptions struct {
8990
Annotations []string `mapstructure:"annotations" yaml:",omitempty"`
9091
Force bool `mapstructure:"force" yaml:",omitempty"`
9192
ServiceAccount string `mapstructure:"service-account" yaml:",omitempty"`
93+
Dependencies []string `mapstructure:"dependencies" yaml:",omitempty"`
9294
}
9395

9496
func (o *bindCmdOptions) preRunE(cmd *cobra.Command, args []string) error {
@@ -194,7 +196,7 @@ func (o *bindCmdOptions) run(cmd *cobra.Command, args []string) error {
194196

195197
name := o.nameFor(source, sink)
196198

197-
binding := v1.Pipe{
199+
pipe := v1.Pipe{
198200
ObjectMeta: metav1.ObjectMeta{
199201
Namespace: o.Namespace,
200202
Name: name,
@@ -205,61 +207,65 @@ func (o *bindCmdOptions) run(cmd *cobra.Command, args []string) error {
205207
},
206208
}
207209

210+
if o.Dependencies != nil {
211+
pipe.Spec.Dependencies = o.Dependencies
212+
}
213+
208214
if o.ErrorHandler != "" {
209215
if errorHandler, err := o.parseErrorHandler(); err == nil {
210-
binding.Spec.ErrorHandler = errorHandler
216+
pipe.Spec.ErrorHandler = errorHandler
211217
} else {
212218
return err
213219
}
214220
}
215221

216222
if len(o.Steps) > 0 {
217-
binding.Spec.Steps = make([]v1.Endpoint, 0)
223+
pipe.Spec.Steps = make([]v1.Endpoint, 0)
218224
for idx, stepDesc := range o.Steps {
219225
stepIndex := idx + 1
220226
stepKey := fmt.Sprintf("%s%d", stepKeyPrefix, stepIndex)
221227
step, err := o.decode(stepDesc, stepKey)
222228
if err != nil {
223229
return err
224230
}
225-
binding.Spec.Steps = append(binding.Spec.Steps, step)
231+
pipe.Spec.Steps = append(pipe.Spec.Steps, step)
226232
}
227233
}
228234

229235
if len(o.Traits) > 0 {
230-
if binding.Annotations == nil {
231-
binding.Annotations = make(map[string]string)
236+
if pipe.Annotations == nil {
237+
pipe.Annotations = make(map[string]string)
232238
}
233239

234240
for _, t := range o.Traits {
235241
kv := strings.SplitN(t, "=", 2)
236242
if len(kv) != 2 {
237243
return fmt.Errorf("could not parse trait configuration %s, expected format 'trait.property=value'", t)
238244
}
239-
value := maybeBuildArrayNotation(binding.Annotations[v1.TraitAnnotationPrefix+kv[0]], kv[1])
240-
binding.Annotations[v1.TraitAnnotationPrefix+kv[0]] = value
245+
value := maybeBuildArrayNotation(pipe.Annotations[v1.TraitAnnotationPrefix+kv[0]], kv[1])
246+
pipe.Annotations[v1.TraitAnnotationPrefix+kv[0]] = value
241247
}
242248
}
243249

244250
if o.ServiceAccount != "" {
245-
binding.Spec.ServiceAccountName = o.ServiceAccount
251+
pipe.Spec.ServiceAccountName = o.ServiceAccount
246252
}
247253

248254
// --operator-id={id} is a syntax sugar for '--annotation camel.apache.org/operator.id={id}'
249-
binding.SetOperatorID(strings.TrimSpace(o.OperatorID))
255+
pipe.SetOperatorID(strings.TrimSpace(o.OperatorID))
250256

251257
for _, annotation := range o.Annotations {
252258
parts := strings.SplitN(annotation, "=", 2)
253259
if len(parts) == 2 {
254-
binding.Annotations[parts[0]] = parts[1]
260+
pipe.Annotations[parts[0]] = parts[1]
255261
}
256262
}
257263

258264
if o.OutputFormat != "" {
259-
return showPipeOutput(cmd, &binding, o.OutputFormat, client.GetScheme())
265+
return showPipeOutput(cmd, &pipe, o.OutputFormat, client.GetScheme())
260266
}
261267

262-
replaced, err := kubernetes.ReplaceResource(o.Context, client, &binding)
268+
replaced, err := kubernetes.ReplaceResource(o.Context, client, &pipe)
263269
if err != nil {
264270
return err
265271
}

pkg/cmd/bind_test.go

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -277,3 +277,28 @@ func TestBindOutputWithoutKubernetesCluster(t *testing.T) {
277277
_, err = ExecuteCommand(bindCmd, cmdBind, "my:src", "my:dst", "-o", "yaml")
278278
require.NoError(t, err)
279279
}
280+
281+
func TestBindOutputWithDependencies(t *testing.T) {
282+
buildCmdOptions, bindCmd, _ := initializeBindCmdOptions(t)
283+
output, err := ExecuteCommand(bindCmd, cmdBind, "my:src", "my:dst", "-o", "yaml", "-d", "camel:my-comp", "-d", "mvn:my-dep")
284+
assert.Equal(t, "yaml", buildCmdOptions.OutputFormat)
285+
286+
require.NoError(t, err)
287+
assert.Equal(t, `apiVersion: camel.apache.org/v1
288+
kind: Pipe
289+
metadata:
290+
annotations:
291+
camel.apache.org/operator.id: camel-k
292+
creationTimestamp: null
293+
name: my-to-my
294+
spec:
295+
dependencies:
296+
- camel:my-comp
297+
- mvn:my-dep
298+
sink:
299+
uri: my:dst
300+
source:
301+
uri: my:src
302+
status: {}
303+
`, output)
304+
}

pkg/cmd/run.go

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -83,7 +83,7 @@ func newCmdRun(rootCmdOptions *RootCmdOptions) (*cobra.Command, *runCmdOptions)
8383

8484
cmd.Flags().String("name", "", "The integration name")
8585
cmd.Flags().String("image", "", "An image built externally (ie, via CICD). Enabling it will skip the Integration build phase.")
86-
cmd.Flags().StringArrayP("dependency", "d", nil, `A dependency that should be included, e.g., "-d camel:mail" for a Camel component, "-d mvn:org.my:app:1.0" for a Maven dependency`)
86+
cmd.Flags().StringArrayP("dependency", "d", nil, `A dependency that should be included, e.g., "camel:mail" for a Camel component, "mvn:org.my:app:1.0" for a Maven dependency`)
8787
cmd.Flags().BoolP("wait", "w", false, "Wait for the integration to be running")
8888
cmd.Flags().StringP("kit", "k", "", "The kit used to run the integration")
8989
cmd.Flags().StringArrayP("property", "p", nil, "Add a runtime property or a local properties file from a path "+

pkg/controller/pipe/initialize_test.go

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -185,6 +185,7 @@ func TestNewPipe(t *testing.T) {
185185
Name: "my-sink",
186186
},
187187
},
188+
Dependencies: []string{"camel:management", "mvn:org.acme:jdbc-driver:1.0.0"},
188189
},
189190
}
190191
c, err := internal.NewFakeClient(pipe, &source, &sink)
@@ -204,6 +205,8 @@ func TestNewPipe(t *testing.T) {
204205
require.NoError(t, err)
205206
assert.Equal(t, pipe.Name, expectedIT.Name)
206207
assert.Equal(t, v1.IntegrationPhaseNone, expectedIT.Status.Phase)
208+
assert.Contains(t, expectedIT.Spec.Dependencies, "camel:management")
209+
assert.Contains(t, expectedIT.Spec.Dependencies, "mvn:org.acme:jdbc-driver:1.0.0")
207210
assert.Equal(t, "Pipe", expectedIT.Labels[kubernetes.CamelCreatorLabelKind])
208211
assert.Equal(t, "my-pipe", expectedIT.Labels[kubernetes.CamelCreatorLabelName])
209212
flow, err := json.Marshal(expectedIT.Spec.Flows[0].RawMessage)

0 commit comments

Comments
 (0)