Compare commits

...

213 Commits

Author SHA1 Message Date
Albert Callarisa edb70cf461
Merge pull request #1520 from acroca/set-scheduler-binding-address-on-init
feat: Allow configuring the scheduler host on init
2025-07-14 18:11:26 -07:00
Yaron Schneider 22536a9640
Merge pull request #1438 from KentHsu/fix-perfsprint-linter-error
fix perfsprint linter error
2025-07-02 10:56:08 -07:00
KentHsu fff4c9158f fix linter error
Signed-off-by: KentHsu <chiahaohsu9@gmail.com>
2025-05-13 22:09:22 +08:00
Kent (Chia-Hao), Hsu 3198d9ca7e
Merge branch 'master' into fix-perfsprint-linter-error 2025-05-13 22:07:20 +08:00
Yaron Schneider b51eab0d84
Merge pull request #1509 from twinguy/master
Add detection for incompatible flags with --run-file
2025-05-05 18:59:17 -07:00
twinguy b31a9f2c56
chore: added go mod tidy to clear up pipeline issues
Signed-off-by: twinguy <twinguy17@gmail.com>
2025-04-14 21:37:58 -05:00
twinguy c939814420
Use compatibleflags approach instead of incompatible
Signed-off-by: twinguy <twinguy17@gmail.com>
2025-04-11 21:43:37 -05:00
Yaron Schneider a85b8132db
Merge branch 'master' into fix-perfsprint-linter-error 2025-03-29 00:40:15 +03:00
twinguy 5da3528524
Remove deprecated tests
Signed-off-by: twinguy <twinguy17@gmail.com>
2025-03-24 16:56:21 -05:00
twinguy e7c1a322d7
Refactor warning message for incompatible flags in --run-file
Signed-off-by: twinguy <twinguy17@gmail.com>
2025-03-24 16:32:13 -05:00
twinguy ce0b9fb4d9
Add detection for incompatible flags with --run-file
Signed-off-by: twinguy <twinguy17@gmail.com>
2025-03-23 23:39:44 -05:00
Yaron Schneider 29f8962111
Merge release 1.15 into master (#1499)
* use non-deprecated flags in List operation (#1478)

Signed-off-by: yaron2 <schneider.yaron@live.com>

* Scheduler: set broadcast address to localhost:50006 in selfhosted (#1480)

* Scheduler: set broadcast address to localhost:50006 in selfhosted

Signed-off-by: joshvanl <me@joshvanl.dev>

* Set schedulder override flag for edge and dev

Signed-off-by: joshvanl <me@joshvanl.dev>

---------

Signed-off-by: joshvanl <me@joshvanl.dev>

* Fix scheduler broadcast address for windows (#1481)

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Remove deprecated flags (#1482)

* remove deprecated flags

Signed-off-by: yaron2 <schneider.yaron@live.com>

* update Dapr version in tests

Signed-off-by: yaron2 <schneider.yaron@live.com>

---------

Signed-off-by: yaron2 <schneider.yaron@live.com>

* Fix daprsystem configuration retrieval when renewing certificates (#1486)

The issue found when similar resource were installed in k8s that use the name "configurations".
In this case the knative's "configurations.serving.knative.dev/v1" was the last in the list and the command returned the error
`Error from server (NotFound): configurations.serving.knative.dev "daprsystem" not found`

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix: arguments accept units (#1490)

* fix: arguments accept units
`max-body-size` and `read-buffer-size` now accept units as defined in the docs.

Fixes #1489

Signed-off-by: Mike Nguyen <hey@mike.ee>

* chore: gofumpt

Signed-off-by: Mike Nguyen <hey@mike.ee>

* refactor: modify logic to comply with vetting

Signed-off-by: Mike Nguyen <hey@mike.ee>

* chore: gofumpt -w .

Signed-off-by: Mike Nguyen <hey@mike.ee>

* refactor: set defaults
`max-body-size` is defaulted to 4Mi
`request-buffer-size` is defaulted to 4Ki

This is inline with the runtime.

Signed-off-by: Mike Nguyen <hey@mike.ee>

* fix: set defaults in run and annotate

Signed-off-by: Mike Nguyen <hey@mike.ee>

* chore: gofumpt

Signed-off-by: Mike Nguyen <hey@mike.ee>

* refactor: exit with error rather than panic

Co-authored-by: Anton Troshin <troll.sic@gmail.com>
Signed-off-by: Mike Nguyen <hey@mike.ee>

---------

Signed-off-by: Mike Nguyen <hey@mike.ee>
Co-authored-by: Anton Troshin <troll.sic@gmail.com>

* Fix scheduler pod count for 1.15 version when testing master and latest (#1492)

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix podman CI (#1493)

* Fix podman CI
Update to podman 5.4.0

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix --cpus flag

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix dapr upgrade command incorrectly detecting HA mode for new version 1.15 (#1494)

* Fix dapr upgrade command detecting HA mode for new version 1.15
The issue is that the scheduler by default uses 3 replicas, which incorrectly identified non-HA install as HA.

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix e2e

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix scheduler address for dapr run with file on Windows (#1497)

Signed-off-by: Anton Troshin <anton@diagrid.io>

* release: test upgrade/downgrade for 1.13/1.14/1.15 + mariner (#1491)

* release: test upgrade/downgrade for 1.13/1.14/1.15 + mariner

Signed-off-by: Mike Nguyen <hey@mike.ee>

* fix: version skews

Co-authored-by: Anton Troshin <troll.sic@gmail.com>
Signed-off-by: Mike Nguyen <hey@mike.ee>

* Update tests/e2e/upgrade/upgrade_test.go

Accepted

Co-authored-by: Anton Troshin <troll.sic@gmail.com>
Signed-off-by: Yaron Schneider <schneider.yaron@live.com>

* Update tests/e2e/upgrade/upgrade_test.go

Co-authored-by: Anton Troshin <troll.sic@gmail.com>
Signed-off-by: Yaron Schneider <schneider.yaron@live.com>

* Fix downgrade issue from 1.15 by deleting previous version scheduler pods
Update 1.15 RC to latest RC.18

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix downgrade 1.15 to 1.13 scenario with 0 scheduler pods

Signed-off-by: Anton Troshin <anton@diagrid.io>

* increase update test timeout to 60m and update latest version to 1.15

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix httpendpoint tests cleanup and checks

Signed-off-by: Anton Troshin <anton@diagrid.io>

* make sure matrix runs appropriate tests, every matrix ran the same tests

Signed-off-by: Anton Troshin <anton@diagrid.io>

* skip TestKubernetesRunFile on HA

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix skip TestKubernetesRunFile on HA

Signed-off-by: Anton Troshin <anton@diagrid.io>

* update to latest dapr 1.15.2

Signed-off-by: Anton Troshin <anton@diagrid.io>

* add logs when waiting for pod deletion

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Mike Nguyen <hey@mike.ee>
Signed-off-by: Yaron Schneider <schneider.yaron@live.com>
Signed-off-by: Anton Troshin <anton@diagrid.io>
Co-authored-by: Anton Troshin <anton@diagrid.io>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
Co-authored-by: Anton Troshin <troll.sic@gmail.com>

* Fix dapr init test latest version retrieval (#1500)

Lint

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix downgrade stuck (#1501)

* Fix goroutine channel leaks and ensure proper cleanup in tests

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Add artificial delay before deleting scheduler pods during downgrade

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Add timeout to helm upgrade tests, they are being stuck sometime for 5+ minutes

Signed-off-by: Anton Troshin <anton@diagrid.io>

* bump helm.sh/helm/v3 to v3.17.1

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: yaron2 <schneider.yaron@live.com>
Signed-off-by: joshvanl <me@joshvanl.dev>
Signed-off-by: Anton Troshin <anton@diagrid.io>
Signed-off-by: Mike Nguyen <hey@mike.ee>
Signed-off-by: Yaron Schneider <schneider.yaron@live.com>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
Co-authored-by: Josh van Leeuwen <me@joshvanl.dev>
Co-authored-by: Mike Nguyen <hey@mike.ee>
2025-03-13 18:36:13 -07:00
Anton Troshin 16aeac5701
Merge branch 'master' into merge-release-1.15-into-master 2025-03-13 18:01:03 -05:00
Anton Troshin 16cc1d1b59
Fix downgrade stuck (#1501)
* Fix goroutine channel leaks and ensure proper cleanup in tests

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Add artificial delay before deleting scheduler pods during downgrade

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Add timeout to helm upgrade tests, they are being stuck sometime for 5+ minutes

Signed-off-by: Anton Troshin <anton@diagrid.io>

* bump helm.sh/helm/v3 to v3.17.1

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-03-12 18:27:40 -07:00
Anton Troshin ecc4ea4953
Fix dapr init test latest version retrieval (#1500)
Lint

Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-03-07 13:42:23 -08:00
Mike Nguyen 4c1c26f2b6
release: test upgrade/downgrade for 1.13/1.14/1.15 + mariner (#1491)
* release: test upgrade/downgrade for 1.13/1.14/1.15 + mariner

Signed-off-by: Mike Nguyen <hey@mike.ee>

* fix: version skews

Co-authored-by: Anton Troshin <troll.sic@gmail.com>
Signed-off-by: Mike Nguyen <hey@mike.ee>

* Update tests/e2e/upgrade/upgrade_test.go

Accepted

Co-authored-by: Anton Troshin <troll.sic@gmail.com>
Signed-off-by: Yaron Schneider <schneider.yaron@live.com>

* Update tests/e2e/upgrade/upgrade_test.go

Co-authored-by: Anton Troshin <troll.sic@gmail.com>
Signed-off-by: Yaron Schneider <schneider.yaron@live.com>

* Fix downgrade issue from 1.15 by deleting previous version scheduler pods
Update 1.15 RC to latest RC.18

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix downgrade 1.15 to 1.13 scenario with 0 scheduler pods

Signed-off-by: Anton Troshin <anton@diagrid.io>

* increase update test timeout to 60m and update latest version to 1.15

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix httpendpoint tests cleanup and checks

Signed-off-by: Anton Troshin <anton@diagrid.io>

* make sure matrix runs appropriate tests, every matrix ran the same tests

Signed-off-by: Anton Troshin <anton@diagrid.io>

* skip TestKubernetesRunFile on HA

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix skip TestKubernetesRunFile on HA

Signed-off-by: Anton Troshin <anton@diagrid.io>

* update to latest dapr 1.15.2

Signed-off-by: Anton Troshin <anton@diagrid.io>

* add logs when waiting for pod deletion

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Mike Nguyen <hey@mike.ee>
Signed-off-by: Yaron Schneider <schneider.yaron@live.com>
Signed-off-by: Anton Troshin <anton@diagrid.io>
Co-authored-by: Anton Troshin <anton@diagrid.io>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
Co-authored-by: Anton Troshin <troll.sic@gmail.com>
2025-03-05 17:19:56 -08:00
Anton Troshin a0921c7820
Fix scheduler address for dapr run with file on Windows (#1497)
Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-03-05 17:18:23 -08:00
Anton Troshin 6c9bcc6dcf
Fix dapr upgrade command incorrectly detecting HA mode for new version 1.15 (#1494)
* Fix dapr upgrade command detecting HA mode for new version 1.15
The issue is that the scheduler by default uses 3 replicas, which incorrectly identified non-HA install as HA.

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix e2e

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-02-26 10:08:12 -08:00
Anton Troshin 42b93eaa7a
Merge branch 'master' into fix-perfsprint-linter-error 2025-02-24 11:13:45 -06:00
Anton Troshin 98b9da9699
Fix scheduler pod count for 1.15 version when testing master and latest (#1488)
Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-02-24 09:11:00 -08:00
Anton Troshin bd09c94b77
Fix podman CI (#1493)
* Fix podman CI
Update to podman 5.4.0

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix --cpus flag

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-02-24 09:07:42 -08:00
Anton Troshin 06f38ed9bc
Fix scheduler pod count for 1.15 version when testing master and latest (#1492)
Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-02-21 19:11:41 -08:00
Mike Nguyen 0cd0585b64
fix: arguments accept units (#1490)
* fix: arguments accept units
`max-body-size` and `read-buffer-size` now accept units as defined in the docs.

Fixes #1489

Signed-off-by: Mike Nguyen <hey@mike.ee>

* chore: gofumpt

Signed-off-by: Mike Nguyen <hey@mike.ee>

* refactor: modify logic to comply with vetting

Signed-off-by: Mike Nguyen <hey@mike.ee>

* chore: gofumpt -w .

Signed-off-by: Mike Nguyen <hey@mike.ee>

* refactor: set defaults
`max-body-size` is defaulted to 4Mi
`request-buffer-size` is defaulted to 4Ki

This is inline with the runtime.

Signed-off-by: Mike Nguyen <hey@mike.ee>

* fix: set defaults in run and annotate

Signed-off-by: Mike Nguyen <hey@mike.ee>

* chore: gofumpt

Signed-off-by: Mike Nguyen <hey@mike.ee>

* refactor: exit with error rather than panic

Co-authored-by: Anton Troshin <troll.sic@gmail.com>
Signed-off-by: Mike Nguyen <hey@mike.ee>

---------

Signed-off-by: Mike Nguyen <hey@mike.ee>
Co-authored-by: Anton Troshin <troll.sic@gmail.com>
2025-02-21 08:11:11 -08:00
Anton Troshin 728b329ce5
Merge branch 'master' into fix-perfsprint-linter-error 2025-02-18 10:28:56 -06:00
Anton Troshin a968b18f08
Fix daprsystem configuration retrieval when renewing certificates (#1486)
The issue found when similar resource were installed in k8s that use the name "configurations".
In this case the knative's "configurations.serving.knative.dev/v1" was the last in the list and the command returned the error
`Error from server (NotFound): configurations.serving.knative.dev "daprsystem" not found`

Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-02-14 17:49:29 -08:00
Yaron Schneider ac6822ea69
Remove deprecated flags (#1482)
* remove deprecated flags

Signed-off-by: yaron2 <schneider.yaron@live.com>

* update Dapr version in tests

Signed-off-by: yaron2 <schneider.yaron@live.com>

---------

Signed-off-by: yaron2 <schneider.yaron@live.com>
2025-02-03 13:27:22 -08:00
Anton Troshin f8ee63c8f4
Fix scheduler broadcast address for windows (#1481)
Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-01-31 12:34:07 -08:00
Josh van Leeuwen 8ce6b9fed9
Scheduler: set broadcast address to localhost:50006 in selfhosted (#1480)
* Scheduler: set broadcast address to localhost:50006 in selfhosted

Signed-off-by: joshvanl <me@joshvanl.dev>

* Set schedulder override flag for edge and dev

Signed-off-by: joshvanl <me@joshvanl.dev>

---------

Signed-off-by: joshvanl <me@joshvanl.dev>
2025-01-27 10:16:37 -08:00
Yaron Schneider 953c4a2a3f
use non-deprecated flags in List operation (#1478)
Signed-off-by: yaron2 <schneider.yaron@live.com>
2025-01-21 22:52:26 -08:00
Mike Nguyen c3f0fb2472
release: pin go to 1.23.5 (#1477)
Signed-off-by: mikeee <hey@mike.ee>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
2025-01-20 16:50:10 -08:00
Mike Nguyen 3acfa7d7e4
fix: population of the schedulerhostaddress in self-hosted mode (#1475)
* fix: population of the schedulerhostaddress in self-hosted mode

The scheduler host address is pre-populated when using the self-hosted mode multi-app run similarly to the single app run.
Kubernetes multi-app run is not affected and you will still need to specify a scheduler host address.

Signed-off-by: mikeee <hey@mike.ee>

* chore: lint

Signed-off-by: mikeee <hey@mike.ee>

---------

Signed-off-by: mikeee <hey@mike.ee>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
2025-01-20 14:18:31 -08:00
Mike Nguyen 104849bc74
chore: remove gopkg / cleanup repo (#1415)
* chore: remove gopkg

Signed-off-by: mikeee <hey@mike.ee>

* chore: upgrade actions versions and remove explicit caching steps

Signed-off-by: mikeee <hey@mike.ee>

---------

Signed-off-by: mikeee <hey@mike.ee>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
2025-01-15 05:28:22 -08:00
Anton Troshin 17f4785906
Update dependencies, Go version and address CVEs (#1474)
* Update dependencies, Go version and address CVEs

Signed-off-by: Anton Troshin <anton@diagrid.io>

* update golangci-lint version and list of disabled linters form dapr/dapr

Signed-off-by: Anton Troshin <anton@diagrid.io>

* adjust golangci-lint settings and fix lint issues

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix test

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>
2025-01-09 14:16:44 -08:00
Filinto Duran efe1d6c1e2
add image pull policy (#1462)
* add image pull policy

Signed-off-by: Filinto Duran <filinto@diagrid.io>

* add allowed values

Signed-off-by: Filinto Duran <filinto@diagrid.io>

* feedback refactor allowed values name

Signed-off-by: Filinto Duran <filinto@diagrid.io>

* add unit tests

Signed-off-by: Filinto Duran <filinto@diagrid.io>

* lint

Signed-off-by: Filinto Duran <filinto@diagrid.io>

* lint

Signed-off-by: Filinto Duran <filinto@diagrid.io>

* more lint

Signed-off-by: Filinto Duran <filinto@diagrid.io>

* more lint

Signed-off-by: Filinto Duran <filinto@diagrid.io>

---------

Signed-off-by: Filinto Duran <filinto@diagrid.io>
Co-authored-by: Anton Troshin <anton@diagrid.io>
Co-authored-by: Mike Nguyen <hey@mike.ee>
2025-01-07 09:09:00 -08:00
Mike Nguyen dbbe022a8a
fix: allow the scheduler client to initialise for edge builds (#1467)
Signed-off-by: mikeee <hey@mike.ee>
2024-11-26 13:09:01 -08:00
Anton Troshin 25d9ece42f
Add version parsing check skip malformed versions and avoid panic (#1469)
* Add version parsing check skip malformed versions and avoid panic

Signed-off-by: Anton Troshin <anton@diagrid.io>

* lint

Signed-off-by: Anton Troshin <anton@diagrid.io>

* do not return error on nil, skip bad versions

Signed-off-by: Anton Troshin <anton@diagrid.io>

* simplify condition to skip prerelease and versions with metadata
print warning on error and non-semver version tag

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-11-22 13:59:51 -08:00
Anton Troshin 6d5e64d964
Fix tests running master in CI with specific dapr version (#1461)
* Fix tests running master in CI with specific dapr version

Signed-off-by: Anton Troshin <anton@diagrid.io>

* move env version load into common

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix k8s test files

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Revert "fix k8s test files"

This reverts commit 344867d19ca4b38e5a83a82a2a00bb04c1775bab.

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Revert "move env version load into common"

This reverts commit 39e8c8caf54a157464bb44dffe448fc75727487f.

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Revert "Fix tests running master in CI with specific dapr version"

This reverts commit a02c81f7e25a6bbdb8e3b172a8e215dae60d321f.

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Add GetRuntimeVersion to be able to compare semver dapr versions for conditional tests
Use GetRuntimeVersion in test

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-11-08 10:33:08 -08:00
Yaron Schneider 8cd81b0477
Merge pull request #1460 from antontroshin/merge-release-1.14-to-master
Merge release 1.14 to master
2024-11-05 17:29:12 -08:00
Anton Troshin 5446171840
Add versioned pod number validation
Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-11-05 17:38:38 -06:00
Anton Troshin 1152a1ef55
Add placement and scheduler in slim mode self-hosted tests
Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-11-05 16:22:01 -06:00
Anton Troshin d781b03002
Change podman mount to home
Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-11-05 03:07:52 -06:00
Anton Troshin 9bc96c2fa0
Fix test
Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-11-05 02:11:25 -06:00
Anton Troshin 376690b43e
Fix number of HA mode pods to wait in tests
Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-11-05 01:35:53 -06:00
Anton Troshin 086a3b9adb
Fix number of pods to wait in tests
Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-11-05 01:09:47 -06:00
Anton Troshin 1f080952a5
Add logs
Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-11-05 00:56:45 -06:00
Anton Troshin 002a223864
Merge branch 'master' into merge-release-1.14-to-master 2024-11-04 20:14:52 -06:00
Anton Troshin db712e7eed
Fixing e2e tests, podman and scheduler fail with mariner images (#1450)
* Fix standalone e2e tests
Fix podman e2e install
Fix scheduler start failure on standalone mariner image variant

Signed-off-by: Anton Troshin <anton@diagrid.io>

* fix test

Signed-off-by: Anton Troshin <anton@diagrid.io>

* revert

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix podman machine settings
Add cleanups
Remove parallel tests
Fix mariner volume mount location
Remove old build tags

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-10-01 09:19:35 -07:00
Yetkin Timocin a3571c8464
Fix a typo (#1453)
Signed-off-by: ytimocin <ytimocin@microsoft.com>
2024-10-01 09:17:12 -07:00
Josh van Leeuwen e08443b9b3
Remove Docker client dependency from standalone run (#1443)
Signed-off-by: joshvanl <me@joshvanl.dev>
2024-08-15 13:53:26 -07:00
Yaron Schneider aefcca1899
Merge branch 'master' into fix-perfsprint-linter-error 2024-08-13 18:21:22 -07:00
Rishab Kumar aa0436ebe0
Added new holopin cli badge (#1399)
Signed-off-by: Rishab Kumar <rishabkumar7@gmail.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Mike Nguyen <hey@mike.ee>
2024-08-06 14:08:58 -07:00
Yaron Schneider 027f5da3e1
update redis version (#1439)
Signed-off-by: yaron2 <schneider.yaron@live.com>
2024-07-25 09:58:14 -07:00
KentHsu 22059c399e fix perfsprint linter error
Signed-off-by: KentHsu <chiahaohsu9@gmail.com>
2024-07-24 11:12:02 +08:00
Yaron Schneider fecf47d752
pin bitnami chart version for redis (#1437)
Signed-off-by: yaron2 <schneider.yaron@live.com>
2024-07-23 15:49:14 -07:00
Anton Troshin ad67ce58c4
Add dapr scheduler server to the status command (#1434)
Signed-off-by: Anton Troshin <anton@diagrid.io>
2024-07-22 16:38:06 -07:00
Cassie Coyle e72f95393c
Fix Scheduler Data Dir Permissions Issue (#1432)
* fix w/ @joshvanl & anton

Signed-off-by: Cassandra Coyle <cassie@diagrid.io>

* add a .

Signed-off-by: Cassandra Coyle <cassie@diagrid.io>

---------

Signed-off-by: Cassandra Coyle <cassie@diagrid.io>
2024-07-19 11:49:08 -07:00
Josh van Leeuwen 16a513ba7a
Change scheduler container data dir from `/var/run/...` to `/var/lib`. (#1429)
Signed-off-by: joshvanl <me@joshvanl.dev>
2024-07-18 16:29:43 -07:00
Josh van Leeuwen 30d888f4e6
Fix dapr init scheduler (#1428)
* Add E2E to validate scheduler after init.

Signed-off-by: Artur Souza <asouza.pro@gmail.com>

* Adds dapr_scheduler verify container

Signed-off-by: joshvanl <me@joshvanl.dev>

* Assert eventually TCP connect

Signed-off-by: joshvanl <me@joshvanl.dev>

* Fix eventually t check

Signed-off-by: joshvanl <me@joshvanl.dev>

* Write etcd-data-dir to custom path with volume

Signed-off-by: joshvanl <me@joshvanl.dev>

* Adds Helpers to test funcs

Signed-off-by: joshvanl <me@joshvanl.dev>

* Adds container name to TCP check

Signed-off-by: joshvanl <me@joshvanl.dev>

* Use rc.3 for scheduler

Signed-off-by: joshvanl <me@joshvanl.dev>

* Print container logs on failed TCP conn

Signed-off-by: joshvanl <me@joshvanl.dev>

* Fix params

Signed-off-by: joshvanl <me@joshvanl.dev>

* Use b

Signed-off-by: joshvanl <me@joshvanl.dev>

* Addfs `dev` flag to rc init

Signed-off-by: joshvanl <me@joshvanl.dev>

* Fix version check

Signed-off-by: joshvanl <me@joshvanl.dev>

* Skip TCP check on slim mode

Signed-off-by: joshvanl <me@joshvanl.dev>

* Remove debug test code

Signed-off-by: joshvanl <me@joshvanl.dev>

---------

Signed-off-by: Artur Souza <asouza.pro@gmail.com>
Signed-off-by: joshvanl <me@joshvanl.dev>
Co-authored-by: Artur Souza <asouza.pro@gmail.com>
2024-07-18 12:50:16 -07:00
Josh van Leeuwen 29d29ab549
Give scheduler a default volume, making it resilient to restarts by (#1423)
* Give scheduler a default volume, making it resilient to restarts by
default

Signed-off-by: joshvanl <me@joshvanl.dev>

* Remove dapr_scheduler volume on uninstall, gated by `--all`

Signed-off-by: joshvanl <me@joshvanl.dev>

* Fix containerErrs in standaone.go

Signed-off-by: joshvanl <me@joshvanl.dev>

* Do not attempt to delete scheduler volume if no container runtime

Signed-off-by: joshvanl <me@joshvanl.dev>

* Increase upgrade test timeout to 40m

Signed-off-by: joshvanl <me@joshvanl.dev>

---------

Signed-off-by: joshvanl <me@joshvanl.dev>
Co-authored-by: Artur Souza <artursouza.ms@outlook.com>
2024-07-17 12:13:51 -07:00
Yaron Schneider ddf43a5f55
update link (#1426)
Signed-off-by: yaron2 <schneider.yaron@live.com>
2024-07-16 23:42:12 -07:00
Josh van Leeuwen ad3442b252
dapr_scheduler: Adds scheduler-volume flag (#1422)
* dapr_scheduler: pre-create data dir

Signed-off-by: joshvanl <me@joshvanl.dev>

* Adds --scheduler-volume to specify volume for data directory

Signed-off-by: joshvanl <me@joshvanl.dev>

---------

Signed-off-by: joshvanl <me@joshvanl.dev>
2024-07-12 08:22:34 -07:00
Mike Nguyen ed0d3af2d0
fix: scheduler host address passed to runtime (#1421)
* fix: scheduler host address passed to runtime

Signed-off-by: mikeee <hey@mike.ee>

* fix: scheduler client stream initialised for 1.14<

Signed-off-by: mikeee <hey@mike.ee>

* fix: modify scheduler host address validation

if the scheduler container is not active, the scheduler flag will
not be passed to the runtime

Signed-off-by: mikeee <hey@mike.ee>

* fix: lint and refactor

Signed-off-by: mikeee <hey@mike.ee>

---------

Signed-off-by: mikeee <hey@mike.ee>
2024-07-10 09:37:34 -07:00
Artur Souza 762e2bb4ac
Fix check for version to contain scheduler. (#1417)
Signed-off-by: Artur Souza <asouza.pro@gmail.com>
2024-07-05 20:16:40 -07:00
Cassie Coyle fd1d8e85bf
Distributed Scheduler CLI Changes (#1405)
* wip

Signed-off-by: Cassandra Coyle <cassie@diagrid.io>

* rm scheduleJob logic. keep only init/uninstall logic

Signed-off-by: Cassandra Coyle <cassie@diagrid.io>

* Fixes install and uninstall of scheduler in standalone mode.

Signed-off-by: Artur Souza <asouza.pro@gmail.com>

* Fixing path for Go tools in Darwin.

Signed-off-by: Artur Souza <asouza.pro@gmail.com>

* Fix Go bin location for MacOS.

Signed-off-by: Artur Souza <asouza.pro@gmail.com>

* Fix min scheduler version to be 1.14.x

Signed-off-by: Artur Souza <asouza.pro@gmail.com>

* Use env var to pass scheduler host.

Signed-off-by: Artur Souza <asouza.pro@gmail.com>

* Fix CLI build to work with latest MacOS runners from GH

Signed-off-by: Artur Souza <asouza.pro@gmail.com>

---------

Signed-off-by: Cassandra Coyle <cassie@diagrid.io>
Signed-off-by: Artur Souza <asouza.pro@gmail.com>
Co-authored-by: Artur Souza <asouza.pro@gmail.com>
2024-07-03 14:58:55 -07:00
dependabot[bot] 4881ca11d7
Bump golang.org/x/net from 0.21.0 to 0.23.0 (#1401)
Bumps [golang.org/x/net](https://github.com/golang/net) from 0.21.0 to 0.23.0.
- [Commits](https://github.com/golang/net/compare/v0.21.0...v0.23.0)

---
updated-dependencies:
- dependency-name: golang.org/x/net
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2024-05-14 20:01:32 +05:30
Josh van Leeuwen 619cd9cd84
Update dependencies for v1.13.0-rc.6 release (#1383)
* Update dependencies for v1.13.0-rc.1 release

Signed-off-by: joshvanl <me@joshvanl.dev>

* Update tests/e2e/upgrade/upgrade_test.go

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* Update github.com/dapr/go-sdk to v1.9.1

Signed-off-by: joshvanl <me@joshvanl.dev>

* Ping go-sdk to joshvanl main fork

Signed-off-by: joshvanl <me@joshvanl.dev>

* Update and fix e2e tests in standalone mode

Signed-off-by: joshvanl <me@joshvanl.dev>

* Set correct rc version

Signed-off-by: joshvanl <me@joshvanl.dev>

* Revert go.mod to keep requires for kube & docker auth

Signed-off-by: joshvanl <me@joshvanl.dev>

* Update dapr/dapr to v1.13.0-rc.2

Signed-off-by: joshvanl <me@joshvanl.dev>

* Update to use rc to 2

Signed-off-by: joshvanl <me@joshvanl.dev>

* Update github.com/dapr/go-sdk to main

Signed-off-by: joshvanl <me@joshvanl.dev>

* Update to 1.13.0-rc.6

Signed-off-by: joshvanl <me@joshvanl.dev>

* Fix func name call

Signed-off-by: joshvanl <me@joshvanl.dev>

---------

Signed-off-by: joshvanl <me@joshvanl.dev>
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2024-02-16 11:37:37 -08:00
dependabot[bot] 3ea5f9c6b2
Bump github.com/opencontainers/runc from 1.1.5 to 1.1.12 (#1380)
Bumps [github.com/opencontainers/runc](https://github.com/opencontainers/runc) from 1.1.5 to 1.1.12.
- [Release notes](https://github.com/opencontainers/runc/releases)
- [Changelog](https://github.com/opencontainers/runc/blob/v1.1.12/CHANGELOG.md)
- [Commits](https://github.com/opencontainers/runc/compare/v1.1.5...v1.1.12)

---
updated-dependencies:
- dependency-name: github.com/opencontainers/runc
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2024-02-07 13:20:32 +05:30
dependabot[bot] 1da8760f11
Bump github.com/lestrrat-go/jwx/v2 from 2.0.12 to 2.0.19 (#1377)
Bumps [github.com/lestrrat-go/jwx/v2](https://github.com/lestrrat-go/jwx) from 2.0.12 to 2.0.19.
- [Release notes](https://github.com/lestrrat-go/jwx/releases)
- [Changelog](https://github.com/lestrrat-go/jwx/blob/develop/v2/Changes)
- [Commits](https://github.com/lestrrat-go/jwx/compare/v2.0.12...v2.0.19)

---
updated-dependencies:
- dependency-name: github.com/lestrrat-go/jwx/v2
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2024-01-23 20:33:22 -08:00
twinguy 2380446870
fix default installation directory permissions (#1375)
Signed-off-by: Kenny Meador <kenny.meador@outlook.com>
Signed-off-by: Kenny Meador <kmeador@dollargeneral.com>
Co-authored-by: Kenny Meador <kmeador@dollargeneral.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2024-01-23 16:00:06 +05:30
Luis Rascão 50e1dffec0
Fix flaky upgrade test (#1368)
* Fix flaky upgrade test

Signed-off-by: Luis Rascao <luis.rascao@gmail.com>

* fixup! Fix flaky upgrade test

Signed-off-by: Luis Rascao <luis.rascao@gmail.com>

---------

Signed-off-by: Luis Rascao <luis.rascao@gmail.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2024-01-23 15:25:30 +05:30
Mukundan Sundararajan f5eb4fda6c
fix upload artifact name conflict (#1373)
* fix upload test report name

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix linter errors

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix upload artifacts version and name conflicts

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix typo

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix typo

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

---------

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2024-01-18 02:07:09 -08:00
Pravin Pushkar c7e8612b11
Upgrade go to 1.21 (#1331)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-12-18 23:36:54 -08:00
Stuart Leeks 668bab451d
Add --run-file support for stdin (#1364)
If the run-file argument is speficied as '-', read the config file from stdin

Signed-off-by: Stuart Leeks <stuartle@microsoft.com>
2023-11-22 07:04:02 -08:00
dependabot[bot] a339bdf491
Bump google.golang.org/grpc from 1.57.0 to 1.57.1 (#1362)
Bumps [google.golang.org/grpc](https://github.com/grpc/grpc-go) from 1.57.0 to 1.57.1.
- [Release notes](https://github.com/grpc/grpc-go/releases)
- [Commits](https://github.com/grpc/grpc-go/compare/v1.57.0...v1.57.1)

---
updated-dependencies:
- dependency-name: google.golang.org/grpc
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2023-10-26 12:48:03 +05:30
dependabot[bot] ac0a3cb06f
Bump golang.org/x/net from 0.15.0 to 0.17.0 (#1356)
Bumps [golang.org/x/net](https://github.com/golang/net) from 0.15.0 to 0.17.0.
- [Commits](https://github.com/golang/net/compare/v0.15.0...v0.17.0)

---
updated-dependencies:
- dependency-name: golang.org/x/net
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2023-10-12 23:35:55 +05:30
Mukundan Sundararajan d55944ccec
Merge pull request #1358 from mukundansundar/merge_rel_1.12_master
Merge rel 1.12 master
2023-10-12 04:54:22 -07:00
Mukundan Sundararajan 02eec8bbc8
Merge branch 'master' into merge_rel_1.12_master 2023-10-12 04:15:14 -07:00
Mukundan Sundararajan 1d60280de4
update dapr runtime to v1.12.0 (#1357)
* update dapr runtime to v1.12.0

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix dashboard version

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

---------

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-10-12 07:45:22 +05:30
Shubham Sharma 0c1c275972
Upgrade runtime and go-sdk versions (#1355)
Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2023-10-11 13:15:09 +05:30
Mukundan Sundararajan bb2c3a7f66
Merge pull request #1350 from mukundansundar/merge_rel_1.12_master
Merge release 1.12 master
2023-10-04 00:15:03 -07:00
Pravin Pushkar 7a09fd6b9c
Merge branch 'master' into merge_rel_1.12_master 2023-10-04 09:30:30 +05:30
hdget a08eebb5db
create dapr install dir before copy (#1112)
Signed-off-by: hdget <hdget@qq.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
2023-10-03 13:17:49 -07:00
Pravin Pushkar a38a44d27b
update runtime RC to RC.5 (#1353)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-10-03 09:37:51 -07:00
Mukundan Sundararajan 6a85f487e7 Merge branch 'release-1.12' into merge_rel_1.12_master 2023-10-03 17:51:00 +05:30
Mukundan Sundararajan df8f242fc8
add appconfig default config for dev mode multi-app run k8s (#1352)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-10-03 17:34:40 +05:30
Mukundan Sundararajan 3fe6d8fffd
Merge branch 'master' into merge_rel_1.12_master 2023-09-29 10:44:21 -07:00
Mukundan Sundararajan 0ebded24f7
upgrade k8s client (#1349)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-09-29 18:06:56 +05:30
Pravin Pushkar 504d4eadba
Removing preview feature for dapr run -f (#1348)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-09-27 09:03:24 -07:00
Marc Duiker 235f40cf81
Add holopin.yml config (#1344)
Signed-off-by: Marc Duiker <marcduiker@users.noreply.github.com>
2023-09-21 10:41:53 +05:30
Josh van Leeuwen 0c99afb4db
Updates dapr/dapr to v1.12 (#1342)
* Updates the Dapr version to v1.12.0-rc.1

Signed-off-by: joshvanl <me@joshvanl.dev>

* Use correct rc tag name

Signed-off-by: joshvanl <me@joshvanl.dev>

* Fix string match on `HTTP server is running on port x`

Signed-off-by: joshvanl <me@joshvanl.dev>

* Fix error string check for `internal gRPC server`

Signed-off-by: joshvanl <me@joshvanl.dev>

* Update dapr/dapr to 1.12.0-rc.3

Signed-off-by: joshvanl <me@joshvanl.dev>

* Rolling restart the sidecar injector during a restart

Signed-off-by: joshvanl <me@joshvanl.dev>

* Linting

Signed-off-by: joshvanl <me@joshvanl.dev>

* Fix string matching on dapr app output logs

Signed-off-by: joshvanl <me@joshvanl.dev>

* Increase e2e tests `20m` -> `25m`

Signed-off-by: joshvanl <me@joshvanl.dev>

---------

Signed-off-by: joshvanl <me@joshvanl.dev>
2023-09-20 18:19:32 +05:30
Mukundan Sundararajan 41f324016e
adding e2e test for multi app run k8s (#1336)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-09-04 20:28:08 +05:30
Mukundan Sundararajan a15a3eb856
Initial implementation of multi app run for Kubernetes Dev (#1333)
* initial commit for multi-app run k8s impl

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix import

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* move runfileconfig

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* add protobuf conflict warn env

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* Add pubsub component. Check before component creation.

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix e2e

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix e2e

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix e2e

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* address review comments.

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

---------

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-09-04 08:42:58 +05:30
Pravin Pushkar 6738eefe2b
Multiapp run and stop implementation for windows (#1315)
* windows impl for multiapp run

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Uncommenting run on windows

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix static checks

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Kill children and grand children forcefully

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* ommiting tests for wiondows

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* rename method

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* shut down all processes

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Use job handle and named evens together to kill the processes

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* lint fix

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* revert wait to kill

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Adding E2E for windows template file run

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* rename job name

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* build failure

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-08-30 11:06:40 +05:30
Pravin Pushkar 4d586752bc
Self Hosted E2E - fail-fast set to false (#1334)
* fail-fast set to false

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* add TODO

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-08-30 10:39:15 +05:30
Anton Troshin 60f50e3497
Add health and metrics port mapping for placement stand-alone mode (#1323)
* Add health and metrics port mapping for placement stand-alone mode

Signed-off-by: Anton Troshin <anton@diagrid.io>

* move ports declaration to const

Signed-off-by: Anton Troshin <anton@diagrid.io>

* Fix linter check: appendCombine: can combine chain of 3 appends into one (gocritic)

Signed-off-by: Anton Troshin <anton@diagrid.io>

---------

Signed-off-by: Anton Troshin <anton@diagrid.io>
Co-authored-by: Artur Souza <artursouza.ms@outlook.com>
2023-08-09 00:17:49 +05:30
Alessandro (Ale) Segala 650fd6fe8d
Add APP_PROTOCOL env (#1318)
Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
2023-08-07 12:37:34 +05:30
Pravin Pushkar 31b9ea27ae
add release doc (#1325)
* add release doc

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Apply suggestions from code review

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Update release.md

Sample PR

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Update docs/development/release.md

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
2023-07-05 07:42:24 -07:00
Mohit Pal Singh 2751f5fa74
Fix for Quote in username errors dapr init #972 (#1322)
* Fix for Quote in username errors dapr init #972

Signed-off-by: mrmtheboss <starktony239@gmail.com>

* addressed a GitHub Actions Check failure

Signed-off-by: mrmtheboss <starktony239@gmail.com>

* Addressed Shubham's comments

Signed-off-by: Mohit Pal Singh <mohit.pal.singh@outlook.com>

* Addressed Shubham's new comments

Signed-off-by: Mohit Pal Singh <mohit.pal.singh@outlook.com>

* Addressed a GitHub actions failure

Signed-off-by: Mohit Pal Singh <mohit.pal.singh@outlook.com>

* Update utils/utils.go

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Mohit Pal Singh <mohit.pal.singh@outlook.com>

* Added Unit test for SanitizeDir() in utils/utils_test.go

Signed-off-by: Mohit Pal Singh <mohit.pal.singh@outlook.com>

* Addressed a GitHub actions failure

Signed-off-by: Mohit Pal Singh <mohit.pal.singh@outlook.com>

* Update comment.

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

---------

Signed-off-by: mrmtheboss <starktony239@gmail.com>
Signed-off-by: Mohit Pal Singh <mohit.pal.singh@outlook.com>
Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: mrmtheboss <starktony239@gmail.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
2023-06-26 11:50:24 -07:00
Vishal Yadav a4f924f49d
Adding warning for uninstall all while container runtime not running (#1310)
Signed-off-by: Vishal Yadav <vishalydv.me@gmail.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
2023-06-20 10:10:57 +05:30
Shivam Kumar Singh 7da8bd7b15
shivam-51: Add log file paths to dapr list 1228 (#1296)
* shivam-51: Add log file paths to dapr list 1228

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

* Minor type fix.

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

* Add condition for log file in dapr list

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

* Add tests

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

* Complete tests

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

* Fix failing e2e tests

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

* Use constants

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

* Add success tests

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

* Add proper assert in test

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

* Fix typo

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>

---------

Signed-off-by: Shivam Kumar Singh <shivamhere247@gmail.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-06-13 18:34:03 +05:30
Alessandro (Ale) Segala fa2c99d8b0
Update dev container (#1314) 2023-06-13 01:26:54 -07:00
Mukundan Sundararajan c41ea8a4d3
Merge pull request #1312 from shubham1172/shubham1172/merge-release-1.11
Merge release-1.11 into master
2023-06-11 22:50:29 -07:00
Shubham Sharma 35f324a09e
Merge branch 'master' into shubham1172/merge-release-1.11 2023-06-10 18:24:23 +05:30
Shubham Sharma 48cd76517f Merge branch 'release-1.11' into shubham1172/merge-release-1.11
Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2023-06-10 16:17:06 +05:30
Shubham Sharma 2a50c8b59a
Prepare for release (#1309)
Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2023-06-09 21:08:44 -07:00
Shubham Sharma 77fbc192ea
Fix checks for container runtime installation (#1307)
* Check container runtime while installing

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Fix lint

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Fix lint (another attempt)

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

---------

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2023-06-09 11:14:23 +05:30
Yaron Schneider fae95a44f0
update to 1.11.0-rc.9 (#1305)
Signed-off-by: yaron2 <schneider.yaron@live.com>
2023-06-07 18:36:27 -07:00
Mukundan Sundararajan ce97fe0d4b
update to use latest runtime rc.6 (#1298)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-05-31 18:17:55 +05:30
Mukundan Sundararajan c3f08b0679
add app channel address flag for run (#1283)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-05-31 05:21:02 -07:00
Pravin Pushkar c65d816612
Move logdestination flag to sharedRunConfig (#1294)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-05-30 21:00:34 -07:00
Sam 96e225432a
feat(httpendpoint): add tests for cli (#1280)
* feat(httpenpoint): add tests for cli

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* feat(httpendpoints): add httpendpoints in another place in tests

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(e2e): adjust checks for httpendpoints

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* tests(e2e): more adjustments for httpendpoints

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(e2e): keep in mind dapr versions for tests

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(e2e): try workaround until 1.11 release

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(e2e): only test httpendpoints on new tests

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(tests): check correct resource output

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* style: make lint

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(tests): only check httpendpoints if opt enabled

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(tests): only check httpendpoints if opt enabled for uninstall

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(e2e): use latest rc

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* style: make lint again

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* test: try this

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(test): correct expected output string

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(tests): master -> rc version

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(tests): acct for ns already being deleted

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* style: make linter happy

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(tests): try a modification

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* build: retrigger build with random comment update

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix(tests): rm extra test case

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix: address pr feedback

Signed-off-by: Samantha Coyle <sam@diagrid.io>

* fix: update based on pr feedback again

Signed-off-by: Samantha Coyle <sam@diagrid.io>

---------

Signed-off-by: Samantha Coyle <sam@diagrid.io>
Co-authored-by: Artur Souza <artursouza.ms@outlook.com>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
2023-05-30 11:25:40 -05:00
Tom Meadows 36a13bc55a
fixed small typo in variables and function call (#1297)
Signed-off-by: chaosinthecrd <tom@tmlabs.co.uk>
2023-05-29 18:08:06 -05:00
Pravin Pushkar af9030a383
Change for multiple resources paths (#1276)
* Initial change for multiple resources paths for normal run

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* multi app run changes for multiple resource paths

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* correct file paths for windows

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* remove checking duplicates

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* addressed review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Fix tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-05-25 07:54:20 -07:00
Pravin Pushkar a59826c0a2
Pinning runtime to 1.11.0-rc.4 (#1284)
* Pinning runtime to 1.11.0-rc.1

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* dashboard release fix

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Fix few more E2E tests failures

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* dashboard version fix on init

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Handle upgrade with dashboard.

Signed-off-by: Artur Souza <asouza.pro@gmail.com>

* fixing modtidy

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* export IsDashboardIncluded to be used in E2E

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* update to use rc.4 version of runtime

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Signed-off-by: Artur Souza <asouza.pro@gmail.com>
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
Co-authored-by: Artur Souza <asouza.pro@gmail.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-05-25 15:23:28 +05:30
Sam 337eab4079
fix(build): add httpendpoint resource (#1285)
Signed-off-by: Samantha Coyle <sam@diagrid.io>
2023-05-19 10:08:32 -07:00
Shubham Sharma 76bf893295
Pin podman to 4.4.4 in self-hosted e2e test (#1279) 2023-05-04 18:21:55 +05:30
Mukundan Sundararajan 90c8d960f2
add timeout for install podman step (#1275)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-04-25 15:58:37 +05:30
Mukundan Sundararajan d3f54cf94b
Add name template (#1274)
* add ability to specify a name for a run template

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix test template

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* move list e2e tests to stop template subtest

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix template name

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* Update cmd/run.go

Co-authored-by: Pravin Pushkar <ppushkar@microsoft.com>
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

---------

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-04-25 15:40:22 +05:30
Artur Souza 81fd09b7d1
Installs,uninstalls,upgrade dapr-dashboard separately when applicable. (#1272)
Signed-off-by: Artur Souza <asouza.pro@gmail.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-04-24 14:05:44 +05:30
Pravin Pushkar 9f67738e24
fix appID reference (#1273)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-04-24 12:14:49 +05:30
Pravin Pushkar 7abf871ce0
Configurable log destination (#1258)
* COnfigurable log destination

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Custom writer impl

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix e2e tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix flaky mar tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* adding e2e for log destination

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* adding tests and change logic to create log file

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* update e2e tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-04-24 11:30:46 +05:30
Mukundan Sundararajan 4e3ae81df5
deprecate app-ssl flag in cli (#1269)
* deprecate app-ssl flag in cli

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* Update cmd/annotate.go

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

---------

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
2023-04-12 21:02:10 -07:00
Tharun K 756b541ae4
handle home directory prefix (#1247)
* handle home directory prefix

Signed-off-by: tharun634 <tharun634@gmail.com>

* add test

Signed-off-by: tharun634 <tharun634@gmail.com>

* lint + remove $HOME prefix

Signed-off-by: tharun634 <tharun634@gmail.com>

* windows check + homeDirPrefix const

Signed-off-by: tharun634 <tharun634@gmail.com>

---------

Signed-off-by: tharun634 <tharun634@gmail.com>
Co-authored-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-04-05 12:03:12 +05:30
dependabot[bot] 808defb16c
Bump github.com/opencontainers/runc from 1.1.2 to 1.1.5 (#1265)
Bumps [github.com/opencontainers/runc](https://github.com/opencontainers/runc) from 1.1.2 to 1.1.5.
- [Release notes](https://github.com/opencontainers/runc/releases)
- [Changelog](https://github.com/opencontainers/runc/blob/v1.1.5/CHANGELOG.md)
- [Commits](https://github.com/opencontainers/runc/compare/v1.1.2...v1.1.5)

---
updated-dependencies:
- dependency-name: github.com/opencontainers/runc
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2023-04-05 11:37:49 +05:30
Girish Sharma 176fa0a663
Use offical gh cli instead of npm github-release-cli (#1264)
Signed-off-by: letmerecall <girishsharma001@gmail.com>
2023-03-30 18:39:26 +05:30
Stuart Leeks 6eca34e727
Update dev container feature docs to include docker (#1263)
Signed-off-by: Stuart Leeks <stuartle@microsoft.com>
2023-03-23 01:00:18 +05:30
Thorsten Hans fff7e75762
Allow setting container-runtime via env var for `dapr init` (#1251)
* Allow specifying container-runtime via env var for `dapr init` (#1210)

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>

* pull default container runtime name from utils instead of introducing a new magic string

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>

* Load config values in the order of  defaults, env vars, flags

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>

* fix(config): load runtime version using proper name

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>

---------

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-03-16 17:51:02 +05:30
Stuart Leeks b60c541241
Add dev container feature (#1233)
* Add dev container feature

Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

* Update docs

Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

* Update README.md

Co-authored-by: Alessandro (Ale) Segala <43508+ItalyPaleAle@users.noreply.github.com>
Signed-off-by: Stuart Leeks <stuart@leeks.net>
Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

* Update README.md

Co-authored-by: Alessandro (Ale) Segala <43508+ItalyPaleAle@users.noreply.github.com>
Signed-off-by: Stuart Leeks <stuart@leeks.net>
Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

* Update dev-container-feature/src/dapr-cli/devcontainer-feature.json

Co-authored-by: Alessandro (Ale) Segala <43508+ItalyPaleAle@users.noreply.github.com>
Signed-off-by: Stuart Leeks <stuart@leeks.net>
Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

* Update dev-container-feature/src/dapr-cli/README.md

Co-authored-by: Alessandro (Ale) Segala <43508+ItalyPaleAle@users.noreply.github.com>
Signed-off-by: Stuart Leeks <stuart@leeks.net>
Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

* Install devcontainer CLI for feature testing

Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

* Ensure curl, check architecture

Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

* PR feedback

Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

* fix indents and config warnings

Signed-off-by: Stuart Leeks <stuartle@microsoft.com>

---------

Signed-off-by: Stuart Leeks <stuartle@microsoft.com>
Signed-off-by: Stuart Leeks <stuart@leeks.net>
Co-authored-by: Alessandro (Ale) Segala <43508+ItalyPaleAle@users.noreply.github.com>
Co-authored-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-03-16 16:07:46 +05:30
Mukundan Sundararajan 45dcd5813d
remove govulncheck from workflow (#1259)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-03-16 12:51:33 +05:30
tianya 72551c95af
output help information when dapr has no parameters (#1255)
Signed-off-by: tianya <tianyax@outlook.com>
2023-03-08 21:26:54 +05:30
Pravin Pushkar 5e3546a351
Init with custom cert (#1249)
* Init with custom cert

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* remove key file

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-03-02 13:31:13 +05:30
dependabot[bot] 55777da7bb
Bump github.com/containerd/containerd from 1.6.15 to 1.6.18 (#1235)
Bumps [github.com/containerd/containerd](https://github.com/containerd/containerd) from 1.6.15 to 1.6.18.
- [Release notes](https://github.com/containerd/containerd/releases)
- [Changelog](https://github.com/containerd/containerd/blob/main/RELEASES.md)
- [Commits](https://github.com/containerd/containerd/compare/v1.6.15...v1.6.18)

---
updated-dependencies:
- dependency-name: github.com/containerd/containerd
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2023-03-02 12:55:01 +05:30
Girish Sharma 17124ebbe9
Upgrade go version to 1.20 (#1246)
* Upgrade go version

Signed-off-by: letmerecall <girishsharma001@gmail.com>

* Upgrade go patch version to get through ci cache

Signed-off-by: letmerecall <girishsharma001@gmail.com>

* Format error message correctly

Signed-off-by: letmerecall <girishsharma001@gmail.com>

* Setup go from go.mod

Signed-off-by: letmerecall <girishsharma001@gmail.com>

* Fix workflow, checkout code before go setup

Signed-off-by: letmerecall <girishsharma001@gmail.com>

* Fix workflow

Signed-off-by: letmerecall <girishsharma001@gmail.com>

---------

Signed-off-by: letmerecall <girishsharma001@gmail.com>
Signed-off-by: Girish Sharma <girishsharma001@gmail.com>
2023-03-02 02:41:17 +05:30
Thorsten Hans 398eb7e24a
Update all actions that relied on Node.JS 12 #1202 (#1252)
Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>
Co-authored-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-03-01 00:41:42 +05:30
Mukundan Sundararajan 56ba05982e
Upgrade linter version to the latest (#1253)
* upgrade golangci-lint version to latest

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix tests

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

---------

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-02-28 23:43:28 +05:30
Thorsten Hans 06a4c6bddc
Show correct container runtime in init logging (#1250)
* Show correct container runtime in init logging

Init logging now logs using container runtime specified by the user instead of always logging "Docker"

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>

#1209

* tests: set test name in test data to remove fmt import

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>

* remove usage of golang.org/x/text and log container runtime names as they are

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>

* ensure modified files do not introduce linting errors

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>

---------

Signed-off-by: Thorsten Hans <thorsten.hans@gmail.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-02-28 23:16:25 +05:30
Taction 211e57b915
Fix unexpected behaviour in dapr list (#1244)
* Fix args parse.

Signed-off-by: zhangchao <zchao9100@gmail.com>

* fix lint

Signed-off-by: zhangchao <zchao9100@gmail.com>

* add e2e test for list

Signed-off-by: zhangchao <zchao9100@gmail.com>

* fix e2e exit to 0

Signed-off-by: zhangchao <zchao9100@gmail.com>

* run dapr run in goroutine

Signed-off-by: zhangchao <zchao9100@gmail.com>

---------

Signed-off-by: zhangchao <zchao9100@gmail.com>
2023-02-28 08:59:24 -08:00
Pravin Pushkar a6f8c7694d
fix go vulerability (#1237)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-02-17 16:38:25 +05:30
Pravin Pushkar a4aafbdfd4
Parallel exec for UTs and cache go dep (#1226)
* Parallel exec for UTs and cache go dep

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* update go version

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-02-17 13:03:20 +05:30
Mukundan Sundararajan de997a9fda
Merge pull request #1234 from pravinpushkar/merge_to_master
Merge to master from release 1.10 branch
2023-02-16 22:27:39 +05:30
Pravin Pushkar 8884bb977e Pin stable runtime dep and merge to master
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-02-16 11:01:19 +05:30
Pravin Pushkar 7e0d9dc45d Merge branch 'master' into release-1.10
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-02-16 11:00:39 +05:30
Pravin Pushkar 63f3fa0e29
fix few issue (#1231)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-02-15 00:31:43 -08:00
Pravin Pushkar 1cec708d88
update runtime to 1.10.0-rc.9 (#1229)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-02-15 11:51:49 +05:30
Yaron Schneider 5ccd602262
Merge pull request #1227 from shivamkm07/fix-wingetcreateFailure
Fix wingetcreate failure
2023-02-14 18:33:30 +00:00
Shivam Kumar 4fdec6b798 re-running tests
Signed-off-by: Shivam Kumar <shivamkm07@gmail.com>
2023-02-14 23:06:02 +05:30
Shivam Kumar 23b37590e4 re-running tests
Signed-off-by: Shivam Kumar <shivamkm07@gmail.com>
2023-02-14 22:42:00 +05:30
Shivam Kumar fffa1dad13 fixing go vulnerability failure
Signed-off-by: Shivam Kumar <shivamkm07@gmail.com>
2023-02-14 21:56:23 +05:30
Shivam Kumar d3c3ac9bba using latest wingetcreate
Signed-off-by: Shivam Kumar <shivamkm07@gmail.com>
2023-02-14 21:32:24 +05:30
Shubham Sharma c8aa85b0e3
Upgrade dapr version to RC 8 (#1223)
Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2023-02-14 11:40:45 +05:30
dependabot[bot] 25cc689143
Bump helm.sh/helm/v3 from 3.10.3 to 3.11.1 (#1217)
Bumps [helm.sh/helm/v3](https://github.com/helm/helm) from 3.10.3 to 3.11.1.
- [Release notes](https://github.com/helm/helm/releases)
- [Commits](https://github.com/helm/helm/compare/v3.10.3...v3.11.1)

---
updated-dependencies:
- dependency-name: helm.sh/helm/v3
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2023-02-13 14:57:35 +05:30
Shivam Kumar 4dd43375e6
Adding more e2e tests for mariner images (#1208)
Signed-off-by: Shivam Kumar <shivamkm07@gmail.com>
2023-02-13 11:40:54 +05:30
Pravin Pushkar 78db061dac
update runtime to RC.6 (#1218)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-02-13 11:40:20 +05:30
Mukundan Sundararajan c1c0ff5193
Merge pull request #1212 from mukundansundar/merge_rel_1.10
partial merge rel 1.10
2023-02-10 12:46:30 +05:30
Mukundan Sundararajan 72c988c476 Merge branch 'release-1.10' into merge_rel_1.10 2023-02-10 11:32:41 +05:30
Mukundan Sundararajan 0c26e1c7a6 Merge branch 'release-1.10' into merge_rel_1.10 2023-02-10 11:15:52 +05:30
Pravin Pushkar 84ba3aad24
E2e fix (#1215)
* fix e2e tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* pass dashboard version to dapr init

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* disable dashboard test for k8s

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* upload run file logs in artifacts

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Revert "upload run file logs in artifacts"

This reverts commit e8343df8bd.

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* trigger pr checks

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-02-09 21:39:42 -08:00
Mukundan Sundararajan e82850a698
update runtime to 1.10-rc.4 (#1213)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-02-07 10:22:02 -08:00
Mukundan Sundararajan 8dbdbc5757 Merge branch 'master' into merge_rel_1.10 2023-02-07 22:11:08 +05:30
Mukundan Sundararajan 20978a2b59
update runtime version to 1.10.0-rc.3. Minor nit fixes (#1207)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-02-06 13:15:47 +05:30
Mukundan Sundararajan a7f06c3b1b
Fix runtime custom path installation logic (#1203)
* fix dapr path version, custom  installation path logic, e2e

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix linter errors

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix paths for windows

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* rename daprPath to daprRuntimePath

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

---------

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-02-05 21:57:23 -08:00
Clay Lenhart 55bc454ad9
correct spelling (#1206) 2023-02-04 23:07:51 -08:00
Pravin Pushkar 38c8f106df
update dapr to 1.10.0-rc.2 (#1201)
* rc.2 changes

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* added test for obfuscation

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-02-02 01:40:55 -08:00
Phillip Hoff 50d5af4cd9
Store app PID in sidecar metadata. (#1200)
* Store app PID in sidecar metadata.

Signed-off-by: Phillip Hoff <phillip@orst.edu>

* Move process check under command check.

Signed-off-by: Phillip Hoff <phillip@orst.edu>

* Add minimal list test appId changes.

Signed-off-by: Phillip Hoff <phillip@orst.edu>

* Reverse params.

Signed-off-by: Phillip Hoff <phillip@orst.edu>

* Proper type conversion.

Signed-off-by: Phillip Hoff <phillip@orst.edu>

---------

Signed-off-by: Phillip Hoff <phillip@orst.edu>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-02-02 11:45:23 +05:30
Alessandro (Ale) Segala a891cb09b3
Update dev container (#1199)
Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
2023-02-02 11:05:32 +05:30
Shubham Sharma 42f9519eb2
Add preview warning to dapr run and add appID and timestamp to logs (#1196)
* Add timestamp to logs and preview warning

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Fix test

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Update log format

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Update log format

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Update comment

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

---------

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2023-02-01 16:19:48 +05:30
Pravin Pushkar 17efdfd4a4
update dapr runtime to 1.10..0-rc.1 (#1194)
* update dapr runtime to 1.10..0-rc.1

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix failure due to runtime changes

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix tests failure

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix import in e2e tests. remove unnecessary uninstall steps

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-31 21:51:57 +05:30
Pravin Pushkar 778b2a5933
dapr stop -f fix and E2E tests for dapr stop and list (#1181)
* E2E tests for dapr stop and list

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* cmdstop to cmdStopWithAppID

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* stop all started processes for dapr apps with kill process group

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* stop all apps in run template test

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* separating os syscall and renaming file

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* moving syscall.go to pkg/syscall

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* name change

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fixed windows error

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* use syscall.kill

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-31 13:07:42 +05:30
Pravin Pushkar b2daa8d220
test on exclude pre-releases from PR checks (#1193)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-01-31 12:36:14 +05:30
Pravin Pushkar 7e00eb4f03
Fix dashboard port conflict message and allow starting on random port (#1189)
* fix dashboard start

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* added comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

---------

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2023-01-31 10:35:02 +05:30
Mukundan Sundararajan da38233cfc
use fqdn for all image names when dockerhub is the registry (#1186)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-27 12:14:28 +05:30
Mukundan Sundararajan 1a9029ce71
change snake_case run template yaml to camelCase (#1183)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-26 21:06:44 -08:00
Mukundan Sundararajan 17dbe5bb13
Add E2E for Run template (#1170)
* refactor run into functions

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* renamed Apps struct as App

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* redirect logs to files. set informational logs. set command dirs

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix linter errors

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix e2e test on non-existent resources-path

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* more fixes

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix merge conflict

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* set default ports for zero values

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix linter errors

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* add more details in error, fix logs in run -f

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* address review comments

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* address review comments

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* add more fixes in template run based on e2e tests

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* add basic happy path e2e for dapr run -f

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* add positive and negative e2e tests for run template

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* address review comments

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-24 10:58:05 -08:00
Pravin Pushkar 14c04f9a87
Dapr stop and list changes for dapr run -f (#1169)
* dapr stop -f impl

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* add description

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix windows failure

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Update cmd/stop.go

Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* change cmd description

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* stop refactoring

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* trigger pr checks

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-24 18:28:31 +05:30
Pravin Pushkar 61bf50cc4c
fix bug in precendence log wrt --dapr-path flag (#1175)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-23 10:23:21 +05:30
Mukundan Sundararajan 36893d9483
Add capability to run to support `-f` flag (#1161)
* refactor run into functions

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* renamed Apps struct as App

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* redirect logs to files. set informational logs. set command dirs

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix linter errors

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix e2e test on non-existent resources-path

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* more fixes

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix merge conflict

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* set default ports for zero values

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix linter errors

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* add more details in error, fix logs in run -f

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* address review comments

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* address review comments

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* add more fixes in template run based on e2e tests

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-20 08:17:34 -08:00
Shubham Sharma b51eda4876
Make JSON and YAML output consistent across `list`, `components`, and `configurations` commands (#1172)
* Fix formatting

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Update UT

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Update UT

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Update E2E

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2023-01-19 23:23:31 -08:00
Pravin Pushkar 9d18f86768
find dapr.yaml in dirpath when dapr run -f <dirpath> is executed (#1166)
* find dapr.yaml in dirpath when dapr run -f <dirpath> is executed

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* modtidy

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* get rid of afero

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* merge fixes

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-19 10:06:01 -08:00
Pravin Pushkar 44d8dcb752
Precedence rule for resources directory, config file and envs (#1158)
* precedence order for resources path and config path

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* env precedence set

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* pass daprInstallPath

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* test dir structure

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* remove hard coded directory structures

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* UT refactor

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* few fixes w.r.t daprPathCmdFlag

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* switching to pre-created test data folder structure

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Move Env to SharedRunConfig struct

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix bug

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* lint fix

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* some refactoring

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-19 22:10:16 +05:30
Pravin Pushkar 8b68de52da
resolve relative path wrt AppDirPath for app specific keys in dapr.yaml (#1164)
* fix absolute path on app cmd

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* using Afero file virtualization for UT

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Revert "using Afero file virtualization for UT"

This reverts commit 8d2f949bd6.

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* adding testdata files

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* resolving app's path wrt AppDirPath

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Revert "adding testdata files"

This reverts commit e3e2012935.

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Revert "fix absolute path on app cmd"

This reverts commit 0e681babbf.

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-11 23:50:55 -08:00
Pravin Pushkar 37c2b34df5
set default fields via struct default tag (#1162)
* set default fields via struct default tag

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* change const name

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* app protocol default

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-11 22:45:42 -08:00
Josh van Leeuwen 87b6f0ebc4
nit: Remove full stop from version string to match other subcommand help output (#1163)
* nit: Remove full stop from version string to match other subcommand help
output

Signed-off-by: joshvanl <me@joshvanl.dev>

* Update cmd/version.go

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Josh van Leeuwen <me@joshvanl.dev>

Signed-off-by: joshvanl <me@joshvanl.dev>
Signed-off-by: Josh van Leeuwen <me@joshvanl.dev>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
2023-01-11 21:25:01 -08:00
Pravin Pushkar c1f9627ed6
Apps run config template parsing (#1152)
* initial commit for run template parsing

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* some code refactor.

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* add some UTs

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* call validate

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* add tests and correct err message

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* refactor Runconfig into 2 structs

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Fix Arg parsing

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix UTs. make app-id be inferred from app-dir if empty

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* put config reltd code into separate folder

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* merge logic for common and apps section of flags.

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* adding tests and few refactoring

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* file close

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* refactor file names

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* resolve path to abs and add more e2e for path resolving

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* address review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* remove getAppskeysmapping

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* add tests, and fix issue for setitng app id when empty.

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-03 17:19:59 +05:30
Shubham Sharma d4654c065b
Add e2e timeout to Dockerhub runs and update Makefile default (#1159)
* Fix e2e test timeout

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Revert unwanted change due to formatting

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Override makefile

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2023-01-03 16:44:50 +05:30
mikeb26 53dff409b4
Support environments with broken $HOME (#1057)
* Support environments with broken $HOME

Currently in standalone mode dapr cli will install the dapr runtime
binaries into $HOME/.dapr. However, in some environments $HOME is
readonly or os.UserHomeDir() can fail (e.g. AWS Lambda). To support
dapr in these environments this change does 2 things:

1. Allows the user to set DAPR_PATH environment variable to indicate
the location of the dapr runtime binaries.

2. Allows the user to optionally specify --dapr-path cli flag to
indicate the location of the dapr runtime binaries. When both
DAPR_PATH environment variable and --dapr-path CLI flag are present,
the cli flag has higher precedence.

When neither DAPR_PATH nor the --dapr-path CLI flag are present, we
fallback to existing behavior of defaulting to $HOME/.dapr.

Signed-off-by: Mike Brown <github@torvosoft.com>

* Address comments

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Address comments

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Address comments

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Fix unit test

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Fix e2e test

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Fix lint

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Mike Brown <github@torvosoft.com>
Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
2023-01-03 15:40:06 +05:30
Shubham Sharma e253b91212
Increase timeout for self hosted e2e tests on MacOS runner (#1157)
* Increase timeout;

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* CaSiNg

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Change TEST_TIMEOUT to E2E_SH_TEST_TIMEOUT

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2022-12-22 12:04:12 +05:30
Pravin Pushkar abe9680b47
dapr init tests without runtime-version flag (#1135)
* dapr init tests without runtime-version

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* introduce new env var to track latest patch release

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Fixes

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* trigger pr check

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* E2E test for init without runtime version in k8s mode

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* updating pinned version to 1.9.4

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* update docs

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix checkmtls failing test due to dir creation

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Revert "fix checkmtls failing test due to dir creation"

This reverts commit 7f2e6031d9.

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix renew cert failing test due to dir creation

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2022-12-20 00:51:59 +05:30
dependabot[bot] 1a980b6f9a
Bump helm.sh/helm/v3 from 3.9.4 to 3.10.3 (#1151)
Bumps [helm.sh/helm/v3](https://github.com/helm/helm) from 3.9.4 to 3.10.3.
- [Release notes](https://github.com/helm/helm/releases)
- [Commits](https://github.com/helm/helm/compare/v3.9.4...v3.10.3)

---
updated-dependencies:
- dependency-name: helm.sh/helm/v3
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2022-12-14 21:54:41 -08:00
Huei Feng 6c1bc5357c
support resources-path (#1012)
* support spec-resources-path

Signed-off-by: HueiFeng <695979933@qq.com>

* Update resource-path

Signed-off-by: hueifeng <695979933@qq.com>

* Update resource-path

Signed-off-by: hueifeng <695979933@qq.com>

* fix

Signed-off-by: hueifeng <695979933@qq.com>

* added deprecation message and e2e tests

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* added messages in readme for deprecation and use of resource-path

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix lint and failing test case

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: HueiFeng <695979933@qq.com>
Signed-off-by: hueifeng <695979933@qq.com>
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Yaron Schneider <schneider.yaron@live.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Pravin Pushkar <ppushkar@microsoft.com>
2022-12-08 01:21:13 -08:00
Pravin Pushkar 63f14c36f9
mariner renew-certificate fix (#1139)
* mariner renew-certificate fix

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* added UT and E2E test

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* lint fix

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Update cmd/renew_certificate.go

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* address review commnets

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* lint fix

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* trigger pr checks

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Update utils/utils_test.go

Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Update utils/utils_test.go

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* Update pkg/kubernetes/renew_certificate.go

Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* added inline comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* trigger pr checks

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* adding usage doc

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2022-12-07 18:14:10 +05:30
Yao Yao 8a0936af9f
About dapr upgrade (#1118) 2022-12-06 09:55:42 +05:30
Shubham Sharma 49a40657d8
Update (#1140)
Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2022-11-30 22:00:44 -08:00
Shubham Sharma e926a0f739
Convert string to lower case (#1137)
Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2022-11-25 10:09:20 +05:30
Pravin Pushkar 544c1d788a
fix getting control plane version (#1116)
* fix getting version

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* changing method to LastIndex

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* refactor UTs and adding additional UT

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix lint

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* comments and prints

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* fix lint

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* review comments

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* re-trigger or check

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* disable foss test

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2022-11-23 14:40:28 +05:30
Shubham Sharma 194ce8a4af
Authenticate requests to GH API to prevent getting throttled (#1134)
* Add authz token

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Change default runtime version to 1.9.4

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Revert whitespace

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Revert

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2022-11-22 15:00:51 +05:30
Albert 13eed0eaf3
Support -dapr-listen-address option to daprd (#1129) 2022-11-18 20:49:31 +05:30
Shubham Sharma db2ba58147
Remove helm dependency from e2e test suite (#1131)
* Replace helm with bash magic

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Revert other auto-save changes

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Extra spaces are prohibited

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Retrigger tests

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Same appraoch for dashboard

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Remove extra var

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Remove extra prefix

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2022-11-17 21:35:26 -08:00
Alex Lai f51aefb0ba
feat: support fish shell completion (#1121)
* feat: support fish shell completion

Signed-off-by: Alex Lai <alexlai97@163.com>

* docs: reword

Signed-off-by: Alex Lai <alexlai97@163.com>

* Update cmd/completion.go

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Alex Lai <alexlai97@outlook.com>
Signed-off-by: Alex Lai <alexlai97@163.com>

* Update cmd/completion.go

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Alex Lai <alexlai97@outlook.com>
Signed-off-by: Alex Lai <alexlai97@163.com>

* docs: fish completion functions to completions folder

[reference](https://fishshell.com/docs/current/completions.html#where-to-put-completions)

Signed-off-by: Alex Lai <alexlai97@163.com>

Signed-off-by: Alex Lai <alexlai97@163.com>
Signed-off-by: Alex Lai <alexlai97@outlook.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Alex Lai <laixingyu@cnaeit.com>
2022-11-07 20:33:10 +05:30
Mukundan Sundararajan 0008d46019
update golang version (#1126)
* update golang version

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* update dapr_cli workflow

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* address comments

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix typo

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2022-11-04 17:11:33 +05:30
Shivam Kumar 0841faf2eb
Updating winget manifests (#1068)
Signed-off-by: shivam <shivamkm07@gmail.com>

Signed-off-by: shivam <shivamkm07@gmail.com>
Co-authored-by: Artur Souza <artursouza.ms@outlook.com>
2022-11-04 16:00:38 +05:30
Mukundan Sundararajan bbcc0bd1c0
upgrade go.mod dependencies (#1110)
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2022-10-18 23:16:53 -07:00
Mukundan Sundararajan 7c302579d6
use latest kind images (#1109)
* use latest kind images. remove fixing of Go patch version

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix typo

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix to Go 1.19.2

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

* fix to Go 1.19.2 in all workflows

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2022-10-18 22:25:21 -07:00
Mukundan Sundararajan da782d1e64
Merge pull request #1106 from pravinpushkar/rel_1.9_to_master
fix kubernetes init to pick correct runtime version (#1103)
2022-10-18 11:11:01 +05:30
Shivam Kumar 3093641fcb fix kubernetes init to pick correct runtime version (#1103)
Signed-off-by: shivam <shivamkm07@gmail.com>

Signed-off-by: shivam <shivamkm07@gmail.com>
2022-10-14 13:34:09 +05:30
Mukundan Sundararajan 87645aaeee
Merge pull request #1101 from pravinpushkar/rel_1.9_to_master
Merge release-1.9 changes into master
2022-10-14 11:36:16 +05:30
Artur Souza eb1dd68a42
Release 1.9 (#1100)
Signed-off-by: Artur Souza <artursouza.ms@outlook.com>

Signed-off-by: Artur Souza <artursouza.ms@outlook.com>
2022-10-13 14:12:07 -07:00
Shubham Sharma 07cf0553dc
Validate and limit container runtime configuration in init and uninstall commands (#1099)
* Limit container runtime

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Lint

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Update docs for container runtime flag

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Add uninstall e2e test

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Update uninstallcmd

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

* Fix skip in e2e

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
2022-10-12 02:47:41 -07:00
Pravin Pushkar 1d0a566a45
Delete remove image logic from uninstall (#1095)
Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2022-10-11 03:01:09 -07:00
Pravin Pushkar 1a3e5d511e
Update redis image to redis:6 (#1096) 2022-10-11 14:30:42 +05:30
Mukundan Sundararajan e2f7e262f1
fix dashboard scheme. fix linter issue (#1092) 2022-10-11 13:15:55 +05:30
Shubham Sharma 8d79ef13ec
Nit: appHealthEnabled => enableAppHealth (#1087)
Signed-off-by: Shubham Sharma <shubhash@microsoft.com>

Signed-off-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2022-10-09 23:21:34 -07:00
Pravin Pushkar 5785c1b59b
Update Dapr RC to 1.9.0-rc.5 (#1086)
* Update Dapr RC to 1.9.0-rc.5

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

* update dashboard depenedency to v0.11.0-rc.1

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>

Signed-off-by: Pravin Pushkar <ppushkar@microsoft.com>
2022-10-09 22:44:52 -07:00
Alessandro (Ale) Segala 657310541a
Add flags for app health checks (#1083)
* Add flags for app health checks

Fixes #1082

Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>

* Added tests

Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>

* 💄

Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>

* Update pkg/standalone/run_test.go

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Alessandro (Ale) Segala <43508+ItalyPaleAle@users.noreply.github.com>

* Update pkg/standalone/run_test.go

Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Signed-off-by: Alessandro (Ale) Segala <43508+ItalyPaleAle@users.noreply.github.com>

* fix go version to 1.19.2

Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>

Signed-off-by: ItalyPaleAle <43508+ItalyPaleAle@users.noreply.github.com>
Signed-off-by: Alessandro (Ale) Segala <43508+ItalyPaleAle@users.noreply.github.com>
Signed-off-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
Co-authored-by: Shubham Sharma <shubhash@microsoft.com>
Co-authored-by: Mukundan Sundararajan <65565396+mukundansundar@users.noreply.github.com>
2022-10-09 21:59:18 -07:00
166 changed files with 11442 additions and 4010 deletions

View File

@ -1,9 +1,7 @@
{
"name": "Dapr CLI Dev Environment",
// Update the container version when you publish dev-container
"image": "ghcr.io/dapr/dapr-dev:0.1.8",
// Replace with uncommented line below to build your own local copy of the image
// "dockerFile": "../docker/Dockerfile-dev",
"image": "ghcr.io/dapr/dapr-dev:latest",
"containerEnv": {
// Uncomment to overwrite devcontainer .kube/config and .minikube certs with the localhost versions
// each time the devcontainer starts, if the respective .kube-localhost/config and .minikube-localhost
@ -14,19 +12,19 @@
// the localhost bind-mount /var/run/docker-host.sock.
// "BIND_LOCALHOST_DOCKER": "true"
},
"extensions": [
"davidanson.vscode-markdownlint",
"golang.go",
"ms-azuretools.vscode-dapr",
"ms-azuretools.vscode-docker",
"ms-kubernetes-tools.vscode-kubernetes-tools"
],
"features": {
"ghcr.io/devcontainers/features/sshd:1": {},
"ghcr.io/devcontainers/features/github-cli:1": {},
"ghcr.io/devcontainers/features/node": {
"version": "lts"
}
},
"mounts": [
// Mount docker-in-docker library volume
"type=volume,source=dind-var-lib-docker,target=/var/lib/docker",
// Bind mount docker socket under an alias to support docker-from-docker
"type=bind,source=/var/run/docker.sock,target=/var/run/docker-host.sock",
"type=bind,source=/var/run/docker.sock,target=/var/run/docker-host.sock"
// Uncomment to clone local .kube/config into devcontainer
// "type=bind,source=${env:HOME}${env:USERPROFILE}/.kube,target=/home/dapr/.kube-localhost",
@ -56,11 +54,28 @@
// Run the entrypoint defined in container image.
"--init"
],
"settings": {
"go.toolsManagement.checkForUpdates": "local",
"go.useLanguageServer": true,
"go.gopath": "/go"
"postCreateCommand": "npm install -g @devcontainers/cli",
"customizations": {
"vscode": {
"extensions": [
"davidanson.vscode-markdownlint",
"golang.go",
"ms-azuretools.vscode-dapr",
"ms-azuretools.vscode-docker",
"ms-kubernetes-tools.vscode-kubernetes-tools"
],
"settings": {
"go.toolsManagement.checkForUpdates": "local",
"go.useLanguageServer": true,
"go.gopath": "/go",
"go.buildTags": "e2e,perf,conftests,unit,integration_test,certtests,allcomponents",
"git.alwaysSignOff": true,
"terminal.integrated.env.linux": {
"GOLANG_PROTOBUF_REGISTRATION_CONFLICT": "ignore"
}
}
}
},
"workspaceFolder": "/workspaces/cli",
"workspaceMount": "type=bind,source=${localWorkspaceFolder},target=/workspaces/cli",
"workspaceMount": "type=bind,source=${localWorkspaceFolder},target=/workspaces/cli"
}

6
.github/holopin.yml vendored Normal file
View File

@ -0,0 +1,6 @@
organization: dapr
defaultSticker: clutq4bgp107990fl1h4m7jp3b
stickers:
-
id: clutq4bgp107990fl1h4m7jp3b
alias: cli-badge

View File

@ -29,8 +29,7 @@ jobs:
name: Build ${{ matrix.target_os }}_${{ matrix.target_arch }} binaries
runs-on: ${{ matrix.os }}
env:
GOVER: 1.19
GOLANG_CI_LINT_VER: v1.49.0
GOLANG_CI_LINT_VER: v1.61.0
GOOS: ${{ matrix.target_os }}
GOARCH: ${{ matrix.target_arch }}
GOPROXY: https://proxy.golang.org
@ -40,7 +39,7 @@ jobs:
WIX_BIN_PATH: 'C:/Program Files (x86)/WiX Toolset v3.11/bin'
strategy:
matrix:
os: [ubuntu-latest, windows-latest, macOS-latest]
os: [ubuntu-latest, windows-latest, macOS-latest, macOS-latest-large]
target_arch: [arm, arm64, amd64]
include:
- os: ubuntu-latest
@ -49,6 +48,8 @@ jobs:
target_os: windows
- os: macOS-latest
target_os: darwin
- os: macOS-latest-large
target_os: darwin
exclude:
- os: windows-latest
target_arch: arm
@ -56,13 +57,28 @@ jobs:
target_arch: arm64
- os: macOS-latest
target_arch: arm
- os: macOS-latest
target_arch: amd64
- os: macOS-latest-large
target_arch: arm
- os: macOS-latest-large
target_arch: arm64
steps:
- name: Set up Go ${{ env.GOVER }}
uses: actions/setup-go@v2
with:
go-version: ${{ env.GOVER }}
- name: Prepare Go's bin location - MacOS
if: matrix.target_os == 'darwin'
run: |
export PATH=$HOME/bin:$PATH
echo "$HOME/bin" >> $GITHUB_PATH
echo "GOBIN=$HOME/bin" >> $GITHUB_ENV
mkdir -p $HOME/bin
- name: Check out code into the Go module directory
uses: actions/checkout@v2
uses: actions/checkout@v4
- name: Set up Go
uses: actions/setup-go@v5
id: setup-go
with:
go-version-file: 'go.mod'
- name: Run golangci-lint
if: matrix.target_arch == 'amd64' && matrix.target_os == 'linux'
uses: golangci/golangci-lint-action@v3.2.0
@ -72,11 +88,6 @@ jobs:
- name: Run make modtidy check-diff
if: matrix.target_arch == 'amd64' && matrix.target_os == 'linux'
run: make modtidy check-diff
- name: Run Go Vulnerability Check
if: matrix.target_arch == 'amd64' && matrix.target_os == 'linux'
run: |
go install golang.org/x/vuln/cmd/govulncheck@latest
govulncheck ./...
- name: Parse release version and set REL_VERSION
run: python ./.github/scripts/get_release_version.py
- name: Setup test output
@ -91,7 +102,7 @@ jobs:
run: make test
- name: Codecov
if: matrix.target_arch == 'amd64' && matrix.target_os == 'linux'
uses: codecov/codecov-action@v1
uses: codecov/codecov-action@v3
- name: Run make release to build and archive binaries
run: |
mkdir -p ${{ env.ARCHIVE_OUTDIR }}
@ -107,14 +118,14 @@ jobs:
if: matrix.target_arch == 'amd64' && matrix.target_os == 'linux'
run: |
[ ! -z "${{ env.REL_VERSION }}" ] && echo "${{ env.REL_VERSION }}" > "${{ env.ARCHIVE_OUTDIR }}/release_version.txt"
- name: upload artifacts
uses: actions/upload-artifact@master
- name: upload artifacts ## Following migration guide in https://github.com/actions/upload-artifact/blob/main/docs/MIGRATION.md
uses: actions/upload-artifact@v4
with:
name: cli_drop
name: cli_drop-${{ matrix.target_os }}_${{ matrix.target_arch }}
path: ${{ env.ARCHIVE_OUTDIR }}
- name: Upload test results
if: always()
uses: actions/upload-artifact@master
uses: actions/upload-artifact@v4
with:
name: ${{ matrix.target_os }}_${{ matrix.target_arch }}_test_unit.json
path: ${{ env.TEST_OUTPUT_FILE }}
@ -127,9 +138,10 @@ jobs:
runs-on: ubuntu-latest
steps:
- name: download artifacts
uses: actions/download-artifact@master
uses: actions/download-artifact@v4
with:
name: cli_drop
pattern: cli_drop-*
merge-multiple: true
path: ${{ env.ARTIFACT_DIR }}
- name: Set Release Version
run: |
@ -144,18 +156,34 @@ jobs:
- name: publish binaries to github
if: startswith(github.ref, 'refs/tags/v')
run: |
echo "installing github-release-cli..."
sudo npm install --silent --no-progress -g github-release-cli@1.3.1
# Get the list of files
RELEASE_ARTIFACT=(${ARTIFACT_DIR}/*)
# Parse repository to get owner and repo names
OWNER_NAME="${GITHUB_REPOSITORY%%/*}"
REPO_NAME="${GITHUB_REPOSITORY#*/}"
export GITHUB_TOKEN=${{ secrets.DAPR_BOT_TOKEN }}
echo "Uploading Dapr CLI Binaries to GitHub Release"
github-release upload \
--owner $OWNER_NAME --repo $REPO_NAME \
--tag "v${REL_VERSION}" \
--name "Dapr CLI v${REL_VERSION}" \
--prerelease true \
gh release create \
"v${REL_VERSION}" \
--title "Dapr CLI v${REL_VERSION}" \
--repo $GITHUB_REPOSITORY \
--prerelease \
${RELEASE_ARTIFACT[*]}
publish-winget:
name: Publish to winget-pkgs
needs: publish
if: startswith(github.ref, 'refs/tags/v')
runs-on: windows-latest
steps:
- name: Check out code
uses: actions/checkout@v4
- name: Parse release version and set REL_VERSION
run: python ./.github/scripts/get_release_version.py
- name: Update winget manifests
shell: pwsh
run: |
$url = "https://github.com/dapr/cli/releases/download/v${{ env.REL_VERSION }}/dapr.msi"
iwr https://aka.ms/wingetcreate/latest -OutFile wingetcreate.exe
if("${{ env.REL_VERSION }}".Contains("-rc.")){
$PackageIdentifier="Dapr.CLI.Preview"
} else{
$PackageIdentifier="Dapr.CLI"
}
.\wingetcreate.exe update "$PackageIdentifier" --submit --urls "$url|x64" --version "${{ env.REL_VERSION }}" --token "${{ secrets.DAPR_BOT_TOKEN }}"

View File

@ -0,0 +1,47 @@
name: "Release dev container features & Generate Documentation"
on:
workflow_dispatch:
jobs:
deploy:
if: ${{ github.ref == 'refs/heads/master' }}
runs-on: ubuntu-latest
permissions:
contents: write
pull-requests: write
packages: write
steps:
- uses: actions/checkout@v4
- name: "Publish Features"
uses: devcontainers/action@v1
with:
publish-features: "true"
base-path-to-features: "./dev-container-feature/src"
generate-docs: "true"
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
- name: Create PR for Documentation
id: push_image_info
env:
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
run: |
set -e
echo "Start."
# Configure git and Push updates
git config --global user.email github-actions@github.com
git config --global user.name github-actions
git config pull.rebase false
branch=automated-documentation-update-$GITHUB_RUN_ID
git checkout -b $branch
message='Automated documentation update'
# Add / update and commit
git add */**/README.md
git commit -m 'Automated documentation update [skip ci]' || export NO_UPDATES=true
# Push
if [ "$NO_UPDATES" != "true" ] ; then
git push origin "$branch"
gh pr create --title "$message" --body "$message"
fi

View File

@ -0,0 +1,62 @@
name: "CI - Test Features"
on:
push:
branches:
- master
pull_request:
paths:
- "dev-container-feature/**"
- .github/workflows/dev_container_feature**
workflow_dispatch:
jobs:
test-autogenerated:
runs-on: ubuntu-latest
continue-on-error: true
strategy:
matrix:
features:
- dapr-cli
baseImage:
- debian:latest
- ubuntu:latest
- mcr.microsoft.com/devcontainers/base:ubuntu
steps:
- uses: actions/checkout@v4
- name: "Install latest devcontainer CLI"
run: npm install -g @devcontainers/cli
- name: "Generating tests for '${{ matrix.features }}' against '${{ matrix.baseImage }}'"
run: devcontainer features test --skip-scenarios -f ${{ matrix.features }} -i ${{ matrix.baseImage }} ./dev-container-feature
test-scenarios:
runs-on: ubuntu-latest
continue-on-error: true
strategy:
matrix:
features:
- dapr-cli
steps:
- uses: actions/checkout@v4
- name: "Install latest devcontainer CLI"
run: npm install -g @devcontainers/cli
- name: "Generating tests for '${{ matrix.features }}' scenarios"
run: devcontainer features test -f ${{ matrix.features }} --skip-autogenerated ./dev-container-feature
test-global:
runs-on: ubuntu-latest
continue-on-error: true
steps:
- uses: actions/checkout@v4
- name: "Install latest devcontainer CLI"
run: npm install -g @devcontainers/cli
- name: "Testing global scenarios"
run: devcontainer features test --global-scenarios-only ./dev-container-feature

View File

@ -0,0 +1,18 @@
name: "Validate devcontainer-feature.json files"
on:
workflow_dispatch:
pull_request:
paths:
- "dev-container-feature/**"
- .github/workflows/dev_container_feature**
jobs:
validate:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: "Validate devcontainer-feature.json files"
uses: devcontainers/action@v1
with:
validate-only: "true"
base-path-to-features: "./dev-container-feature/src"

View File

@ -34,15 +34,16 @@ jobs:
FOSSA_API_KEY: b88e1f4287c3108c8751bf106fb46db6 # This is a push-only token that is safe to be exposed.
steps:
- name: "Checkout code"
uses: actions/checkout@v2
uses: actions/checkout@v4
- name: "Run FOSSA Scan"
uses: fossas/fossa-action@v1.1.0 # Use a specific version if locking is preferred
uses: fossas/fossa-action@v1.3.1 # Use a specific version if locking is preferred
with:
api-key: ${{ env.FOSSA_API_KEY }}
- name: "Run FOSSA Test"
uses: fossas/fossa-action@v1.1.0 # Use a specific version if locking is preferred
with:
api-key: ${{ env.FOSSA_API_KEY }}
run-tests: true
# Disable fossa test due to a bug on fossa side.
# - name: "Run FOSSA Test"
# uses: fossas/fossa-action@v1.3.1 # Use a specific version if locking is preferred
# with:
# api-key: ${{ env.FOSSA_API_KEY }}
# run-tests: true

View File

@ -38,7 +38,7 @@ jobs:
steps:
# Checks-out your repository under $GITHUB_WORKSPACE, so your job can access it
- uses: actions/checkout@v2
- uses: actions/checkout@v4
# Install Dapr
- name: Install DAPR CLI

View File

@ -50,53 +50,43 @@ jobs:
name: E2E tests for K8s (KinD)
runs-on: ubuntu-latest
env:
GOVER: 1.19
DAPR_RUNTIME_VERSION: 1.9.0-rc.3
DAPR_DASHBOARD_VERSION: 0.10.0
DAPR_TGZ: dapr-1.9.0-rc.3.tgz
DAPR_RUNTIME_PINNED_VERSION: 1.14.4
DAPR_DASHBOARD_PINNED_VERSION: 0.14.0
DAPR_RUNTIME_LATEST_STABLE_VERSION:
DAPR_DASHBOARD_LATEST_STABLE_VERSION:
strategy:
fail-fast: false # Keep running if one leg fails.
matrix:
k8s-version:
- v1.21.14
- v1.22.13
- v1.23.10
- v1.24.4
- v1.23.12
- v1.24.6
- v1.25.2
mode:
- ha
- non-ha
# Map between K8s and KinD versions.
# This is attempting to make it a bit clearer what's being tested.
# See: https://github.com/kubernetes-sigs/kind/releases/tag/v0.15.0
# See: https://github.com/kubernetes-sigs/kind/releases/tag/v0.16.0
include:
- k8s-version: v1.21.14
kind-version: v0.15.0
kind-image-sha: sha256:f9b4d3d1112f24a7254d2ee296f177f628f9b4c1b32f0006567af11b91c1f301
- k8s-version: v1.22.13
kind-version: v0.15.0
kind-image-sha: sha256:4904eda4d6e64b402169797805b8ec01f50133960ad6c19af45173a27eadf959
- k8s-version: v1.23.10
kind-version: v0.15.0
kind-image-sha: sha256:f047448af6a656fae7bc909e2fab360c18c487ef3edc93f06d78cdfd864b2d12
- k8s-version: v1.24.4
kind-version: v0.15.0
kind-image-sha: sha256:adfaebada924a26c2c9308edd53c6e33b3d4e453782c0063dc0028bdebaddf98
exclude:
- k8s-version: v1.21.14
mode: non-ha
- k8s-version: v1.21.14
mode: non-ha
- k8s-version: v1.22.13
mode: non-ha
- k8s-version: v1.23.12
kind-version: v0.16.0
kind-image-sha: sha256:9402cf1330bbd3a0d097d2033fa489b2abe40d479cc5ef47d0b6a6960613148a
- k8s-version: v1.24.6
kind-version: v0.16.0
kind-image-sha: sha256:97e8d00bc37a7598a0b32d1fabd155a96355c49fa0d4d4790aab0f161bf31be1
- k8s-version: v1.25.2
kind-version: v0.16.0
kind-image-sha: sha256:9be91e9e9cdf116809841fc77ebdb8845443c4c72fe5218f3ae9eb57fdb4bace
steps:
- name: Set up Go ${{ env.GOVER }}
uses: actions/setup-go@v2
with:
go-version: ${{ env.GOVER }}
- name: Check out code onto GOPATH
uses: actions/checkout@v2
uses: actions/checkout@v4
with:
path: ./src/github.com/dapr/cli
- name: Set up Go
uses: actions/setup-go@v5
id: setup-go
with:
go-version-file: './src/github.com/dapr/cli/go.mod'
- name: Configure KinD
# Generate a KinD configuration file that uses:
@ -124,7 +114,7 @@ jobs:
# Log the generated kind.yaml for easy reference.
cat kind.yaml
- name: Create KinD Cluster
uses: helm/kind-action@v1.0.0
uses: helm/kind-action@v1.3.0
with:
config: kind.yaml
cluster_name: kind
@ -143,16 +133,36 @@ jobs:
- name: Determine latest Dapr Runtime version including Pre-releases
if: github.base_ref == 'master'
run: |
helm repo add dapr https://dapr.github.io/helm-charts/ && helm repo update && export RUNTIME_VERSION=$(helm search repo dapr/dapr --devel --versions | awk '/dapr\/dapr/ {print $3; exit}' )
echo "DAPR_RUNTIME_VERSION=$RUNTIME_VERSION" >> $GITHUB_ENV
echo "Found $RUNTIME_VERSION"
export RUNTIME_VERSION=$(curl -s -H "Authorization: token ${{ secrets.GITHUB_TOKEN }}" https://api.github.com/repos/dapr/dapr/releases | grep tag_name | awk -F':' '{print $2}' | tr -d '", ' | sed '/-/! s/$/_/' | sort -V | sed 's/_$//' | tr -d 'v' | tail -1)
if [[ -z "$RUNTIME_VERSION" ]]; then
echo "Could not fetch the latest Dapr Runtime version. Using pinned version $DAPR_RUNTIME_PINNED_VERSION"
else
echo "Found $RUNTIME_VERSION"
echo "DAPR_RUNTIME_PINNED_VERSION=$RUNTIME_VERSION" >> $GITHUB_ENV
fi
shell: bash
- name: Determine latest Dapr Dashboard version including Pre-releases
if: github.base_ref == 'master'
run: |
curl -L -o dapr.tgz https://github.com/dapr/helm-charts/raw/master/$DAPR_TGZ && tar -xzf dapr.tgz && export DASHBOARD_VERSION=$(cat ./dapr/charts/dapr_dashboard/Chart.yaml | grep version | awk '{ print $2; exit }') && rm -rf dapr
echo "DAPR_DASHBOARD_VERSION=$DASHBOARD_VERSION" >> $GITHUB_ENV
echo "Found $DASHBOARD_VERSION"
export DASHBOARD_VERSION=$(curl -s -H "Authorization: token ${{ secrets.GITHUB_TOKEN }}" https://api.github.com/repos/dapr/dashboard/releases | grep tag_name | awk -F':' '{print $2}' | tr -d '", ' | sed '/-/! s/$/_/' | sort -V | sed 's/_$//' | tr -d 'v' | tail -1)
if [[ -z "$DASHBOARD_VERSION" ]]; then
echo "Could not fetch the latest Dapr Dashboard version. Using pinned version $DAPR_DASHBOARD_PINNED_VERSION"
else
echo "Found $DASHBOARD_VERSION"
echo "DAPR_DASHBOARD_PINNED_VERSION=$DASHBOARD_VERSION" >> $GITHUB_ENV
fi
shell: bash
- name: Determine latest stable Dapr Runtime version
run: |
export LATEST_STABLE_RUNTIME_VERSION=$(curl -s -H "Authorization: token ${{ secrets.GITHUB_TOKEN }}" https://api.github.com/repos/dapr/dapr/releases/latest | grep tag_name | awk -F':' '{print $2}' | tr -d '", ' | sed '/-/! s/$/_/' | sort -V | sed 's/_$//' | tr -d 'v' | tail -1)
echo "Found $LATEST_STABLE_RUNTIME_VERSION"
echo "DAPR_RUNTIME_LATEST_STABLE_VERSION=$LATEST_STABLE_RUNTIME_VERSION" >> $GITHUB_ENV
shell: bash
- name: Determine latest stable Dapr Dashboard version
run: |
export LATEST_STABLE_DASHBOARD_VERSION=$(curl -s -H "Authorization: token ${{ secrets.GITHUB_TOKEN }}" https://api.github.com/repos/dapr/dashboard/releases/latest | grep tag_name | awk -F':' '{print $2}' | tr -d '", ' | sed '/-/! s/$/_/' | sort -V | sed 's/_$//' | tr -d 'v' | tail -1)
echo "Found $LATEST_STABLE_DASHBOARD_VERSION"
echo "DAPR_DASHBOARD_LATEST_STABLE_VERSION=$LATEST_STABLE_DASHBOARD_VERSION" >> $GITHUB_ENV
shell: bash
- name: Run tests with GHCR
# runs every 6hrs
@ -163,6 +173,7 @@ jobs:
export TEST_OUTPUT_FILE=$GITHUB_WORKSPACE/test-e2e-kind.json
echo "TEST_OUTPUT_FILE=$TEST_OUTPUT_FILE" >> $GITHUB_ENV
export GITHUB_TOKEN=${{ secrets.GITHUB_TOKEN }}
export TEST_DAPR_HA_MODE=${{ matrix.mode }}
make e2e-build-run-k8s
shell: bash
- name: Run tests with Docker hub
@ -171,11 +182,12 @@ jobs:
export TEST_OUTPUT_FILE=$GITHUB_WORKSPACE/test-e2e-kind.json
echo "TEST_OUTPUT_FILE=$TEST_OUTPUT_FILE" >> $GITHUB_ENV
export GITHUB_TOKEN=${{ secrets.GITHUB_TOKEN }}
export TEST_DAPR_HA_MODE=${{ matrix.mode }}
make e2e-build-run-k8s
shell: bash
- name: Upload test results
if: always()
uses: actions/upload-artifact@master
uses: actions/upload-artifact@v4
with:
name: ${{ matrix.k8s-version }}_${{ matrix.mode }}_e2e_k8s.json
path: ${{ env.TEST_OUTPUT_FILE }}

View File

@ -10,7 +10,6 @@
# See the License for the specific language governing permissions and
# limitations under the License.
# ------------------------------------------------------------
name: E2E - Self-hosted
on:
@ -19,39 +18,44 @@ on:
- master
- release-*
paths-ignore:
- '**.md'
- "**.md"
schedule:
- cron: '0 */3 * * *'
- cron: '0 */6 * * *'
- cron: "0 */3 * * *"
- cron: "0 */6 * * *"
pull_request:
branches:
- master
- 'release-*'
- "release-*"
paths-ignore:
- '**.md'
- "**.md"
jobs:
self-hosted-e2e:
name: Run Self-Hosted E2E tests in ${{ matrix.target_os }}_${{ matrix.target_arch }}_${{ matrix.dapr_install_mode }}
runs-on: ${{ matrix.os }}
env:
GOVER: 1.19
GOOS: ${{ matrix.target_os }}
GOARCH: ${{ matrix.target_arch }}
GOPROXY: https://proxy.golang.org
ARCHIVE_OUTDIR: dist/archives
DAPR_RUNTIME_VERSION: "1.9.0-rc.3"
DAPR_DASHBOARD_VERSION: 0.10.0
DAPR_TGZ: dapr-1.9.0-rc.3.tgz
DAPR_RUNTIME_PINNED_VERSION: "1.14.4"
DAPR_DASHBOARD_PINNED_VERSION: 0.14.0
DAPR_RUNTIME_LATEST_STABLE_VERSION: ""
DAPR_DASHBOARD_LATEST_STABLE_VERSION: ""
GOLANG_PROTOBUF_REGISTRATION_CONFLICT: warn
PODMAN_VERSION: 5.4.0
strategy:
# TODO: Remove this when our E2E tests are stable for podman on MacOS.
fail-fast: false # Keep running if one leg fails.
matrix:
os: [macos-latest, ubuntu-latest, windows-latest]
# See https://github.com/actions/runner-images
os: [macos-latest-large, ubuntu-latest, windows-latest]
target_arch: [amd64]
dapr_install_mode: [slim, complete]
include:
- os: ubuntu-latest
target_os: linux
- os: macOS-latest
- os: macos-latest-large
target_os: darwin
- os: windows-latest
target_os: windows
@ -59,38 +63,75 @@ jobs:
- os: windows-latest
dapr_install_mode: complete
steps:
- name: Set up Go ${{ env.GOVER }}
uses: actions/setup-go@v2
with:
go-version: ${{ env.GOVER }}
- name: Check out code into the Go module directory
uses: actions/checkout@v2
- name: Install podman - MacOS
if: matrix.os == 'macos-latest' && matrix.dapr_install_mode == 'complete'
- name: Prepare Go's bin location - MacOS
if: matrix.os == 'macos-latest-large'
run: |
sudo rm -rf `brew --cache`
brew upgrade
brew install podman
which podman-mac-helper
podman_helper=$(which podman-mac-helper)
sudo ${podman_helper} install
podman machine init
podman machine start
export PATH=$HOME/bin:$PATH
echo "$HOME/bin" >> $GITHUB_PATH
echo "GOBIN=$HOME/bin" >> $GITHUB_ENV
mkdir -p $HOME/bin
- name: Check out code into the Go module directory
uses: actions/checkout@v4
- name: Set up Go
uses: actions/setup-go@v5
id: setup-go
with:
go-version-file: "go.mod"
- name: Install podman - MacOS
timeout-minutes: 15
if: matrix.os == 'macos-latest-large' && matrix.dapr_install_mode == 'complete'
run: |
# Install podman
curl -sL -o podman.pkg https://github.com/containers/podman/releases/download/v${{ env.PODMAN_VERSION }}/podman-installer-macos-amd64.pkg
sudo installer -pkg podman.pkg -target /
export PATH=/opt/podman/bin:$PATH
echo "/opt/podman/bin" >> $GITHUB_PATH
# Start podman machine
sudo podman-mac-helper install
podman machine init -v $HOME:$HOME --memory 16384 --cpus 12
podman machine start --log-level debug
podman machine ssh sudo sysctl -w kernel.keys.maxkeys=20000
podman info
echo "CONTAINER_RUNTIME=podman" >> $GITHUB_ENV
- name: Determine latest Dapr Runtime version including Pre-releases
if: github.base_ref == 'master'
run: |
helm repo add dapr https://dapr.github.io/helm-charts/ && helm repo update && export RUNTIME_VERSION=$(helm search repo dapr/dapr --devel --versions | awk '/dapr\/dapr/ {print $3; exit}' )
echo "DAPR_RUNTIME_VERSION=$RUNTIME_VERSION" >> $GITHUB_ENV
echo "Found $RUNTIME_VERSION"
export RUNTIME_VERSION=$(curl -s -H "Authorization: token ${{ secrets.GITHUB_TOKEN }}" https://api.github.com/repos/dapr/dapr/releases | grep tag_name | awk -F':' '{print $2}' | tr -d '", ' | sed '/-/! s/$/_/' | sort -V | sed 's/_$//' | tr -d 'v' | tail -1)
if [[ -z "$RUNTIME_VERSION" ]]; then
echo "Could not fetch the latest Dapr Runtime version. Using pinned version $DAPR_RUNTIME_PINNED_VERSION"
else
echo "Found $RUNTIME_VERSION"
echo "DAPR_RUNTIME_PINNED_VERSION=$RUNTIME_VERSION" >> $GITHUB_ENV
fi
shell: bash
- name: Determine latest Dapr Dashboard version including Pre-releases
if: github.base_ref == 'master'
run: |
curl -L -o dapr.tgz https://github.com/dapr/helm-charts/raw/master/$DAPR_TGZ && tar -xzf dapr.tgz && export DASHBOARD_VERSION=$(cat ./dapr/charts/dapr_dashboard/Chart.yaml | grep version | awk '{ print $2; exit }') && rm -rf dapr
echo "DAPR_DASHBOARD_VERSION=$DASHBOARD_VERSION" >> $GITHUB_ENV
echo "Found $DASHBOARD_VERSION"
export DASHBOARD_VERSION=$(curl -s -H "Authorization: token ${{ secrets.GITHUB_TOKEN }}" https://api.github.com/repos/dapr/dashboard/releases | grep tag_name | awk -F':' '{print $2}' | tr -d '", ' | sed '/-/! s/$/_/' | sort -V | sed 's/_$//' | tr -d 'v' | tail -1)
if [[ -z "$DASHBOARD_VERSION" ]]; then
echo "Could not fetch the latest Dapr Dashboard version. Using pinned version $DAPR_DASHBOARD_PINNED_VERSION"
else
echo "Found $DASHBOARD_VERSION"
echo "DAPR_DASHBOARD_PINNED_VERSION=$DASHBOARD_VERSION" >> $GITHUB_ENV
fi
shell: bash
- name: Determine latest stable Dapr Runtime version
run: |
export LATEST_STABLE_RUNTIME_VERSION=$(curl -s -H "Authorization: token ${{ secrets.GITHUB_TOKEN }}" https://api.github.com/repos/dapr/dapr/releases/latest | grep tag_name | awk -F':' '{print $2}' | tr -d '", ' | sed '/-/! s/$/_/' | sort -V | sed 's/_$//' | tr -d 'v' | tail -1)
echo "Found $LATEST_STABLE_RUNTIME_VERSION"
echo "DAPR_RUNTIME_LATEST_STABLE_VERSION=$LATEST_STABLE_RUNTIME_VERSION" >> $GITHUB_ENV
shell: bash
- name: Determine latest stable Dapr Dashboard version
run: |
export LATEST_STABLE_DASHBOARD_VERSION=$(curl -s -H "Authorization: token ${{ secrets.GITHUB_TOKEN }}" https://api.github.com/repos/dapr/dashboard/releases/latest | grep tag_name | awk -F':' '{print $2}' | tr -d '", ' | sed '/-/! s/$/_/' | sort -V | sed 's/_$//' | tr -d 'v' | tail -1)
echo "Found $LATEST_STABLE_DASHBOARD_VERSION"
echo "DAPR_DASHBOARD_LATEST_STABLE_VERSION=$LATEST_STABLE_DASHBOARD_VERSION" >> $GITHUB_ENV
shell: bash
- name: Set the test timeout - MacOS
if: matrix.os == 'macos-latest-large'
run: echo "E2E_SH_TEST_TIMEOUT=30m" >> $GITHUB_ENV
- name: Run E2E tests with GHCR
# runs every 6hrs
if: github.event.schedule == '0 */6 * * *'
@ -98,6 +139,7 @@ jobs:
DAPR_DEFAULT_IMAGE_REGISTRY: ghcr
DAPR_E2E_INIT_SLIM: ${{ contains(matrix.os, 'windows-latest') || contains(matrix.dapr_install_mode, 'slim') }}
CONTAINER_RUNTIME: ${{ env.CONTAINER_RUNTIME }}
E2E_SH_TEST_TIMEOUT: ${{ env.E2E_SH_TEST_TIMEOUT }}
run: |
export TEST_OUTPUT_FILE=$GITHUB_WORKSPACE/test-e2e-standalone.json
echo "TEST_OUTPUT_FILE=$TEST_OUTPUT_FILE" >> $GITHUB_ENV
@ -109,6 +151,7 @@ jobs:
env:
DAPR_E2E_INIT_SLIM: ${{ contains(matrix.os, 'windows-latest') || contains(matrix.dapr_install_mode, 'slim') }}
CONTAINER_RUNTIME: ${{ env.CONTAINER_RUNTIME }}
E2E_SH_TEST_TIMEOUT: ${{ env.E2E_SH_TEST_TIMEOUT }}
run: |
export TEST_OUTPUT_FILE=$GITHUB_WORKSPACE/test-e2e-standalone.json
echo "TEST_OUTPUT_FILE=$TEST_OUTPUT_FILE" >> $GITHUB_ENV
@ -117,8 +160,7 @@ jobs:
shell: bash
- name: Upload test results
if: always()
uses: actions/upload-artifact@master
uses: actions/upload-artifact@v4
with:
name: ${{ matrix.target_os }}_${{ matrix.target_arch }}_e2e_standalone.json
name: ${{ matrix.target_os }}_${{ matrix.target_arch }}_${{ matrix.dapr_install_mode }}_e2e_standalone.json
path: ${{ env.TEST_OUTPUT_FILE }}

View File

@ -49,51 +49,39 @@ jobs:
kubernetes-e2e:
name: Upgrade path tests (KinD)
runs-on: ubuntu-latest
env:
GOVER: 1.19
strategy:
fail-fast: false # Keep running if one leg fails.
matrix:
k8s-version:
- v1.21.14
- v1.22.13
- v1.23.10
- v1.24.4
- v1.23.12
- v1.24.6
- v1.25.2
mode:
- ha
- non-ha
# Map between K8s and KinD versions.
# This is attempting to make it a bit clearer what's being tested.
# See: https://github.com/kubernetes-sigs/kind/releases/tag/v0.15.0
# See: https://github.com/kubernetes-sigs/kind/releases/tag/v0.16.0
include:
- k8s-version: v1.21.14
kind-version: v0.15.0
kind-image-sha: sha256:f9b4d3d1112f24a7254d2ee296f177f628f9b4c1b32f0006567af11b91c1f301
- k8s-version: v1.22.13
kind-version: v0.15.0
kind-image-sha: sha256:4904eda4d6e64b402169797805b8ec01f50133960ad6c19af45173a27eadf959
- k8s-version: v1.23.10
kind-version: v0.15.0
kind-image-sha: sha256:f047448af6a656fae7bc909e2fab360c18c487ef3edc93f06d78cdfd864b2d12
- k8s-version: v1.24.4
kind-version: v0.15.0
kind-image-sha: sha256:adfaebada924a26c2c9308edd53c6e33b3d4e453782c0063dc0028bdebaddf98
exclude:
- k8s-version: v1.21.14
mode: non-ha
- k8s-version: v1.21.14
mode: non-ha
- k8s-version: v1.22.13
mode: non-ha
- k8s-version: v1.23.12
kind-version: v0.16.0
kind-image-sha: sha256:9402cf1330bbd3a0d097d2033fa489b2abe40d479cc5ef47d0b6a6960613148a
- k8s-version: v1.24.6
kind-version: v0.16.0
kind-image-sha: sha256:97e8d00bc37a7598a0b32d1fabd155a96355c49fa0d4d4790aab0f161bf31be1
- k8s-version: v1.25.2
kind-version: v0.16.0
kind-image-sha: sha256:9be91e9e9cdf116809841fc77ebdb8845443c4c72fe5218f3ae9eb57fdb4bace
steps:
- name: Set up Go ${{ env.GOVER }}
uses: actions/setup-go@v2
with:
go-version: ${{ env.GOVER }}
- name: Check out code onto GOPATH
uses: actions/checkout@v2
uses: actions/checkout@v4
with:
path: ./src/github.com/dapr/cli
- name: Set up Go
uses: actions/setup-go@v5
id: setup-go
with:
go-version-file: './src/github.com/dapr/cli/go.mod'
- name: Configure KinD
# Generate a KinD configuration file that uses:
@ -123,7 +111,7 @@ jobs:
cat kind.yaml
- name: Create KinD Cluster
uses: helm/kind-action@v1.0.0
uses: helm/kind-action@v1.3.0
with:
config: kind.yaml
cluster_name: kind
@ -149,6 +137,7 @@ jobs:
run: |
export TEST_OUTPUT_FILE=$GITHUB_WORKSPACE/test-e2e-upgrade-kind.json
echo "TEST_OUTPUT_FILE=$TEST_OUTPUT_FILE" >> $GITHUB_ENV
export TEST_DAPR_HA_MODE=${{ matrix.mode }}
make e2e-build-run-upgrade
- name: Run tests with Docker hub
@ -156,11 +145,12 @@ jobs:
run: |
export TEST_OUTPUT_FILE=$GITHUB_WORKSPACE/test-e2e-upgrade-kind.json
echo "TEST_OUTPUT_FILE=$TEST_OUTPUT_FILE" >> $GITHUB_ENV
export TEST_DAPR_HA_MODE=${{ matrix.mode }}
make e2e-build-run-upgrade
- name: Upload test results
if: always()
uses: actions/upload-artifact@master
uses: actions/upload-artifact@v4
with:
name: ${{ matrix.k8s-version }}_${{ matrix.mode }}_e2e_upgrade_k8s.json
path: ${{ env.TEST_OUTPUT_FILE }}

9
.gitignore vendored
View File

@ -6,6 +6,9 @@
*.dylib
cli
# Handy directory to keep local scripts and help files.
.local/
# Mac's metadata folder
.DS_Store
@ -24,6 +27,10 @@ cli
# CLI's auto-generated components directory
**/components
# Auto generated deploy dir inside .dapr directory
**/.dapr/deploy
# Auto generated logs dir inside .dapr directory
**/.dapr/logs
test_output.json
@ -33,4 +40,4 @@ go.work
#Wix files
*.wixobj
*.wixpdb
*.msi
*.msi

View File

@ -4,7 +4,7 @@ run:
concurrency: 4
# timeout for analysis, e.g. 30s, 5m, default is 1m
deadline: 10m
timeout: 10m
# exit code when at least one issue was found, default is 1
issues-exit-code: 1
@ -16,27 +16,22 @@ run:
#build-tags:
# - mytag
issues:
# which dirs to skip: they won't be analyzed;
# can use regexp here: generated.*, regexp is applied on full path;
# default value is empty list, but next dirs are always skipped independently
# from this option's value:
# third_party$, testdata$, examples$, Godeps$, builtin$
skip-dirs:
exclude-dirs:
- ^pkg.*client.*clientset.*versioned.*
- ^pkg.*client.*informers.*externalversions.*
# which files to skip: they will be analyzed, but issues from them
# won't be reported. Default value is empty list, but there is
# no need to include all autogenerated files, we confidently recognize
# autogenerated files. If it's not please let us know.
skip-files: []
# - ".*\\.my\\.go$"
# - lib/bad.go
- pkg.*mod.*k8s.io.*
# output configuration options
output:
# colored-line-number|line-number|json|tab|checkstyle, default is "colored-line-number"
format: tab
formats:
- format: tab
# print lines of code with issue, default is true
print-issued-lines: true
@ -70,9 +65,6 @@ linters-settings:
statements: 40
govet:
# report about shadowed variables
check-shadowing: true
# settings per analyzer
settings:
printf: # analyzer name, run `go tool vet help` to see all analyzers
@ -81,13 +73,18 @@ linters-settings:
- (github.com/golangci/golangci-lint/pkg/logutils.Log).Warnf
- (github.com/golangci/golangci-lint/pkg/logutils.Log).Errorf
- (github.com/golangci/golangci-lint/pkg/logutils.Log).Fatalf
- github.com/dapr/cli/pkg/print.FailureStatusEvent
- github.com/dapr/cli/pkg/print.SuccessStatusEvent
- github.com/dapr/cli/pkg/print.WarningStatusEvent
- github.com/dapr/cli/pkg/print.InfoStatusEvent
- github.com/dapr/cli/pkg/print.StatusEvent
- github.com/dapr/cli/pkg/print.Spinner
# enable or disable analyzers by name
enable:
- atomicalign
enable-all: false
disable:
- shadow
enable-all: false
disable-all: false
revive:
# linting errors below this confidence will be ignored, default is 0.8
@ -105,9 +102,6 @@ linters-settings:
gocognit:
# minimal code complexity to report, 30 by default (but we recommend 10-20)
min-complexity: 10
maligned:
# print struct with more effective memory layout or not, false by default
suggest-new: true
dupl:
# tokens count to trigger issue, 150 by default
threshold: 100
@ -117,13 +111,11 @@ linters-settings:
# minimal occurrences count to trigger, 3 by default
min-occurrences: 5
depguard:
list-type: blacklist
include-go-root: false
packages:
- github.com/Sirupsen/logrus
packages-with-error-messages:
# specify an error message to output when a blacklisted package is used
github.com/Sirupsen/logrus: "must use github.com/sirupsen/logrus"
rules:
main:
deny:
- pkg: "github.com/Sirupsen/logrus"
desc: "must use github.com/sirupsen/logrus"
misspell:
# Correct spellings using locale preferences for US or UK.
# Default is to use a neutral variety of English.
@ -142,7 +134,7 @@ linters-settings:
# XXX: if you enable this setting, unused will report a lot of false-positives in text editors:
# if it's called for subdir of a project it can't find funcs usages. All text editor integrations
# with golangci-lint call it on a directory with the changed file.
check-exported: false
exported-fields-are-used: false
unparam:
# Inspect exported functions, default is false. Set to true if no external program/library imports your code.
# XXX: if you enable this setting, unparam will report a lot of false-positives in text editors:
@ -215,15 +207,19 @@ linters-settings:
# Allow multiline assignments to be cuddled. Default is true.
allow-multiline-assign: true
# Allow case blocks to end with a whitespace.
allow-case-traling-whitespace: true
# Allow declarations (var) to be cuddled.
allow-cuddle-declarations: false
testifylint:
disable:
- require-error
linters:
fast: false
enable-all: true
disable:
# TODO Enforce the below linters later
- musttag
- dupl
- errcheck
- funlen
@ -232,33 +228,48 @@ linters:
- gocyclo
- gocognit
- godox
- interfacer
- lll
- maligned
- scopelint
- unparam
- wsl
- gomnd
- testpackage
- nestif
- goerr113
- nlreturn
- exhaustive
- gci
- noctx
- exhaustivestruct
- exhaustruct
- gomoddirectives
- paralleltest
- noctx
- gci
- tparallel
- wastedassign
- cyclop
- forbidigo
- tagliatelle
- thelper
- paralleltest
- wrapcheck
- varnamelen
- forcetypeassert
- tagliatelle
- ireturn
- golint
- nosnakecase
- errchkjson
- contextcheck
- gomoddirectives
- godot
- cyclop
- varnamelen
- errorlint
- forcetypeassert
- maintidx
- nilnil
- predeclared
- tenv
- thelper
- wastedassign
- containedctx
- gosimple
- nonamedreturns
- asasalint
- rowserrcheck
- sqlclosecheck
- inamedparam
- tagalign
- mnd
- canonicalheader
- exportloopref
- execinquery
- err113
- fatcontext
- forbidigo

View File

@ -40,7 +40,7 @@ Before you file an issue, make sure you've checked the following:
- 👎 down-vote
1. For bugs
- Check it's not an environment issue. For example, if running on Kubernetes, make sure prerequisites are in place. (state stores, bindings, etc.)
- You have as much data as possible. This usually comes in the form of logs and/or stacktrace. If running on Kubernetes or other environment, look at the logs of the Dapr services (runtime, operator, placement service). More details on how to get logs can be found [here](https://docs.dapr.io/operations/troubleshooting/logs-troubleshooting/).
- You have as much data as possible. This usually comes in the form of logs and/or stacktrace. If running on Kubernetes or other environment, look at the logs of the Dapr services (runtime, operator, placement, scheduler service). More details on how to get logs can be found [here](https://docs.dapr.io/operations/troubleshooting/logs-troubleshooting/).
1. For proposals
- Many changes to the Dapr runtime may require changes to the API. In that case, the best place to discuss the potential feature is the main [Dapr repo](https://github.com/dapr/dapr).
- Other examples could include bindings, state stores or entirely new components.

991
Gopkg.lock generated
View File

@ -1,991 +0,0 @@
# This file is autogenerated, do not edit; changes may be undone by the next 'dep ensure'.
[[projects]]
digest = "1:80004fcc5cf64e591486b3e11b406f1e0d17bf85d475d64203c8494f5da4fcd1"
name = "cloud.google.com/go"
packages = ["compute/metadata"]
pruneopts = "UT"
revision = "8c41231e01b2085512d98153bcffb847ff9b4b9f"
version = "v0.38.0"
[[projects]]
digest = "1:6b1426cad7057b717351eacf5b6fe70f053f11aac1ce254bbf2fd72c031719eb"
name = "contrib.go.opencensus.io/exporter/ocagent"
packages = ["."]
pruneopts = "UT"
revision = "dcb33c7f3b7cfe67e8a2cea10207ede1b7c40764"
version = "v0.4.12"
[[projects]]
digest = "1:b88fe174accff6609eee9dc7e4ec9f828cbda83e3646111538dbcc7f762f1a56"
name = "github.com/Azure/go-autorest"
packages = [
"autorest",
"autorest/adal",
"autorest/azure",
"autorest/date",
"logger",
"tracing",
]
pruneopts = "UT"
revision = "f29a2eccaa178b367df0405778cd85e0af7b4225"
version = "v12.1.0"
[[projects]]
digest = "1:d5e752c67b445baa5b6cb6f8aa706775c2aa8e41aca95a0c651520ff2c80361a"
name = "github.com/Microsoft/go-winio"
packages = [
".",
"pkg/guid",
]
pruneopts = "UT"
revision = "6c72808b55902eae4c5943626030429ff20f3b63"
version = "v0.4.14"
[[projects]]
branch = "master"
digest = "1:174cfc45f3f3e0f24f4bc3d2c80d8bcd4c02e274f9a0c4e7fcb6ff3273c0eeee"
name = "github.com/Pallinder/sillyname-go"
packages = ["."]
pruneopts = "UT"
revision = "97aeae9e6ba11ec62a40cf8b6b4bc42116c0a303"
[[projects]]
digest = "1:04457f9f6f3ffc5fea48e71d62f2ca256637dee0a04d710288e27e05c8b41976"
name = "github.com/Sirupsen/logrus"
packages = ["."]
pruneopts = "UT"
revision = "839c75faf7f98a33d445d181f3018b5c3409a45e"
version = "v1.4.2"
[[projects]]
digest = "1:937ce6e0cd5ccfec205f444a0d9c74f5680cbb68cd0a992b000559bf964ea20b"
name = "github.com/briandowns/spinner"
packages = ["."]
pruneopts = "UT"
revision = "e3fb08e7443c496a847cb2eef48e3883f3e12c38"
version = "v1.6.1"
[[projects]]
digest = "1:c1100fc71e23b6a32b2c68a5202a848fd13811d5a10b12edb8019c3667d1cd9a"
name = "github.com/cenkalti/backoff"
packages = ["."]
pruneopts = "UT"
revision = "4b4cebaf850ec58f1bb1fec5bdebdf8501c2bc3f"
version = "v3.0.0"
[[projects]]
digest = "1:fdb4ed936abeecb46a8c27dcac83f75c05c87a46d9ec7711411eb785c213fa02"
name = "github.com/census-instrumentation/opencensus-proto"
packages = [
"gen-go/agent/common/v1",
"gen-go/agent/metrics/v1",
"gen-go/agent/trace/v1",
"gen-go/metrics/v1",
"gen-go/resource/v1",
"gen-go/trace/v1",
]
pruneopts = "UT"
revision = "a105b96453fe85139acc07b68de48f2cbdd71249"
version = "v0.2.0"
[[projects]]
digest = "1:95ea6524ccf5526a5f57fa634f2789266684ae1c15ce1a0cab3ae68e7ea3c4d0"
name = "github.com/dapr/dapr"
packages = [
"pkg/apis/components",
"pkg/apis/components/v1alpha1",
"pkg/components",
"pkg/config/modes",
]
pruneopts = "UT"
revision = "c75b111b7d2258ce7339f6b40c6d1af5b0b6de22"
version = "v0.2.0"
[[projects]]
digest = "1:ffe9824d294da03b391f44e1ae8281281b4afc1bdaa9588c9097785e3af10cec"
name = "github.com/davecgh/go-spew"
packages = ["spew"]
pruneopts = "UT"
revision = "8991bc29aa16c548c550c7ff78260e27b9ab7c73"
version = "v1.1.1"
[[projects]]
digest = "1:76dc72490af7174349349838f2fe118996381b31ea83243812a97e5a0fd5ed55"
name = "github.com/dgrijalva/jwt-go"
packages = ["."]
pruneopts = "UT"
revision = "06ea1031745cb8b3dab3f6a236daf2b0aa468b7e"
version = "v3.2.0"
[[projects]]
digest = "1:4ddc17aeaa82cb18c5f0a25d7c253a10682f518f4b2558a82869506eec223d76"
name = "github.com/docker/distribution"
packages = [
"digestset",
"reference",
]
pruneopts = "UT"
revision = "2461543d988979529609e8cb6fca9ca190dc48da"
version = "v2.7.1"
[[projects]]
digest = "1:c4c7064c2c67a0a00815918bae489dd62cd88d859d24c95115d69b00b3d33334"
name = "github.com/docker/docker"
packages = [
"api/types",
"api/types/blkiodev",
"api/types/container",
"api/types/events",
"api/types/filters",
"api/types/mount",
"api/types/network",
"api/types/reference",
"api/types/registry",
"api/types/strslice",
"api/types/swarm",
"api/types/time",
"api/types/versions",
"api/types/volume",
"client",
"pkg/tlsconfig",
]
pruneopts = "UT"
revision = "092cba3727bb9b4a2f0e922cd6c0f93ea270e363"
version = "v1.13.1"
[[projects]]
digest = "1:811c86996b1ca46729bad2724d4499014c4b9effd05ef8c71b852aad90deb0ce"
name = "github.com/docker/go-connections"
packages = [
"nat",
"sockets",
"tlsconfig",
]
pruneopts = "UT"
revision = "7395e3f8aa162843a74ed6d48e79627d9792ac55"
version = "v0.4.0"
[[projects]]
digest = "1:e95ef557dc3120984bb66b385ae01b4bb8ff56bcde28e7b0d1beed0cccc4d69f"
name = "github.com/docker/go-units"
packages = ["."]
pruneopts = "UT"
revision = "519db1ee28dcc9fd2474ae59fca29a810482bfb1"
version = "v0.4.0"
[[projects]]
digest = "1:865079840386857c809b72ce300be7580cb50d3d3129ce11bf9aa6ca2bc1934a"
name = "github.com/fatih/color"
packages = ["."]
pruneopts = "UT"
revision = "5b77d2a35fb0ede96d138fc9a99f5c9b6aef11b4"
version = "v1.7.0"
[[projects]]
digest = "1:abeb38ade3f32a92943e5be54f55ed6d6e3b6602761d74b4aab4c9dd45c18abd"
name = "github.com/fsnotify/fsnotify"
packages = ["."]
pruneopts = "UT"
revision = "c2828203cd70a50dcccfb2761f8b1f8ceef9a8e9"
version = "v1.4.7"
[[projects]]
digest = "1:2cd7915ab26ede7d95b8749e6b1f933f1c6d5398030684e6505940a10f31cfda"
name = "github.com/ghodss/yaml"
packages = ["."]
pruneopts = "UT"
revision = "0ca9ea5df5451ffdf184b4428c902747c2c11cd7"
version = "v1.0.0"
[[projects]]
branch = "master"
digest = "1:adddf11eb27039a3afcc74c5e3d13da84e189012ec37acfc2c70385f25edbe0f"
name = "github.com/gocarina/gocsv"
packages = ["."]
pruneopts = "UT"
revision = "2fc85fcf0c07e8bb9123b2104e84cfc2a5b53724"
[[projects]]
digest = "1:4d02824a56d268f74a6b6fdd944b20b58a77c3d70e81008b3ee0c4f1a6777340"
name = "github.com/gogo/protobuf"
packages = [
"proto",
"sortkeys",
]
pruneopts = "UT"
revision = "ba06b47c162d49f2af050fb4c75bcbc86a159d5c"
version = "v1.2.1"
[[projects]]
digest = "1:489a99067cd08971bd9c1ee0055119ba8febc1429f9200ab0bec68d35e8c4833"
name = "github.com/golang/protobuf"
packages = [
"jsonpb",
"proto",
"protoc-gen-go/descriptor",
"protoc-gen-go/generator",
"protoc-gen-go/generator/internal/remap",
"protoc-gen-go/plugin",
"ptypes",
"ptypes/any",
"ptypes/duration",
"ptypes/struct",
"ptypes/timestamp",
"ptypes/wrappers",
]
pruneopts = "UT"
revision = "b5d812f8a3706043e23a9cd5babf2e5423744d30"
version = "v1.3.1"
[[projects]]
digest = "1:a6181aca1fd5e27103f9a920876f29ac72854df7345a39f3b01e61c8c94cc8af"
name = "github.com/google/gofuzz"
packages = ["."]
pruneopts = "UT"
revision = "f140a6486e521aad38f5917de355cbf147cc0496"
version = "v1.0.0"
[[projects]]
digest = "1:582b704bebaa06b48c29b0cec224a6058a09c86883aaddabde889cd1a5f73e1b"
name = "github.com/google/uuid"
packages = ["."]
pruneopts = "UT"
revision = "0cd6bf5da1e1c83f8b45653022c74f71af0538a4"
version = "v1.1.1"
[[projects]]
digest = "1:65c4414eeb350c47b8de71110150d0ea8a281835b1f386eacaa3ad7325929c21"
name = "github.com/googleapis/gnostic"
packages = [
"OpenAPIv2",
"compiler",
"extensions",
]
pruneopts = "UT"
revision = "7c663266750e7d82587642f65e60bc4083f1f84e"
version = "v0.2.0"
[[projects]]
digest = "1:c7810b83a74c6ec1d14d16d4b950c09abce6fbe9cc660ac2cde5b57efa8cc12e"
name = "github.com/gophercloud/gophercloud"
packages = [
".",
"openstack",
"openstack/identity/v2/tenants",
"openstack/identity/v2/tokens",
"openstack/identity/v3/tokens",
"openstack/utils",
"pagination",
]
pruneopts = "UT"
revision = "c2d73b246b48e239d3f03c455905e06fe26e33c3"
version = "v0.1.0"
[[projects]]
digest = "1:4f30fff718a459f9be272e7aa87463cdf4ba27bb8bd7f586ac34c36d670aada4"
name = "github.com/grpc-ecosystem/grpc-gateway"
packages = [
"internal",
"runtime",
"utilities",
]
pruneopts = "UT"
revision = "cddead4ec1d10cc62f08e1fd6f8591fbe71cfff9"
version = "v1.9.1"
[[projects]]
digest = "1:67474f760e9ac3799f740db2c489e6423a4cde45520673ec123ac831ad849cb8"
name = "github.com/hashicorp/golang-lru"
packages = ["simplelru"]
pruneopts = "UT"
revision = "7087cb70de9f7a8bc0a10c375cb0d2280a8edf9c"
version = "v0.5.1"
[[projects]]
digest = "1:c0d19ab64b32ce9fe5cf4ddceba78d5bc9807f0016db6b1183599da3dcc24d10"
name = "github.com/hashicorp/hcl"
packages = [
".",
"hcl/ast",
"hcl/parser",
"hcl/printer",
"hcl/scanner",
"hcl/strconv",
"hcl/token",
"json/parser",
"json/scanner",
"json/token",
]
pruneopts = "UT"
revision = "8cb6e5b959231cc1119e43259c4a608f9c51a241"
version = "v1.0.0"
[[projects]]
digest = "1:a0cefd27d12712af4b5018dc7046f245e1e3b5760e2e848c30b171b570708f9b"
name = "github.com/imdario/mergo"
packages = ["."]
pruneopts = "UT"
revision = "7c29201646fa3de8506f701213473dd407f19646"
version = "v0.3.7"
[[projects]]
digest = "1:870d441fe217b8e689d7949fef6e43efbc787e50f200cb1e70dbca9204a1d6be"
name = "github.com/inconshreveable/mousetrap"
packages = ["."]
pruneopts = "UT"
revision = "76626ae9c91c4f2a10f34cad8ce83ea42c93bb75"
version = "v1.0"
[[projects]]
digest = "1:f5a2051c55d05548d2d4fd23d244027b59fbd943217df8aa3b5e170ac2fd6e1b"
name = "github.com/json-iterator/go"
packages = ["."]
pruneopts = "UT"
revision = "0ff49de124c6f76f8494e194af75bde0f1a49a29"
version = "v1.1.6"
[[projects]]
digest = "1:fa4b4bfa0edfb83c4690d8746ea25bc2447ad0c20063ba72adcb5725f54acde0"
name = "github.com/klauspost/compress"
packages = [
"flate",
"gzip",
"zlib",
]
pruneopts = "UT"
revision = "4e96aec082898e4dad17d8aca1a7e2d01362ff6c"
version = "v1.9.2"
[[projects]]
digest = "1:31e761d97c76151dde79e9d28964a812c46efc5baee4085b86f68f0c654450de"
name = "github.com/konsorten/go-windows-terminal-sequences"
packages = ["."]
pruneopts = "UT"
revision = "f55edac94c9bbba5d6182a4be46d86a2c9b5b50e"
version = "v1.0.2"
[[projects]]
digest = "1:5a0ef768465592efca0412f7e838cdc0826712f8447e70e6ccc52eb441e9ab13"
name = "github.com/magiconair/properties"
packages = ["."]
pruneopts = "UT"
revision = "de8848e004dd33dc07a2947b3d76f618a7fc7ef1"
version = "v1.8.1"
[[projects]]
digest = "1:c658e84ad3916da105a761660dcaeb01e63416c8ec7bc62256a9b411a05fcd67"
name = "github.com/mattn/go-colorable"
packages = ["."]
pruneopts = "UT"
revision = "167de6bfdfba052fa6b2d3664c8f5272e23c9072"
version = "v0.0.9"
[[projects]]
digest = "1:e150b5fafbd7607e2d638e4e5cf43aa4100124e5593385147b0a74e2733d8b0d"
name = "github.com/mattn/go-isatty"
packages = ["."]
pruneopts = "UT"
revision = "c2a7a6ca930a4cd0bc33a3f298eb71960732a3a7"
version = "v0.0.7"
[[projects]]
digest = "1:0356f3312c9bd1cbeda81505b7fd437501d8e778ab66998ef69f00d7f9b3a0d7"
name = "github.com/mattn/go-runewidth"
packages = ["."]
pruneopts = "UT"
revision = "3ee7d812e62a0804a7d0a324e0249ca2db3476d3"
version = "v0.0.4"
[[projects]]
branch = "master"
digest = "1:56aff9bb73896906956fee6927207393212bfaa732c1aab4feaf29de4b1418e9"
name = "github.com/mitchellh/go-ps"
packages = ["."]
pruneopts = "UT"
revision = "621e5597135b1d14a7d9c2bfc7bc312e7c58463c"
[[projects]]
digest = "1:53bc4cd4914cd7cd52139990d5170d6dc99067ae31c56530621b18b35fc30318"
name = "github.com/mitchellh/mapstructure"
packages = ["."]
pruneopts = "UT"
revision = "3536a929edddb9a5b34bd6861dc4a9647cb459fe"
version = "v1.1.2"
[[projects]]
digest = "1:33422d238f147d247752996a26574ac48dcf472976eda7f5134015f06bf16563"
name = "github.com/modern-go/concurrent"
packages = ["."]
pruneopts = "UT"
revision = "bacd9c7ef1dd9b15be4a9909b8ac7a4e313eec94"
version = "1.0.3"
[[projects]]
digest = "1:e32bdbdb7c377a07a9a46378290059822efdce5c8d96fe71940d87cb4f918855"
name = "github.com/modern-go/reflect2"
packages = ["."]
pruneopts = "UT"
revision = "4b7aa43c6742a2c18fdef89dd197aaae7dac7ccd"
version = "1.0.1"
[[projects]]
branch = "master"
digest = "1:6491080aa184f88c2bb8e2f6056e5e0e9a578b2d8666efbd6e97bc37a0c41e72"
name = "github.com/nightlyone/lockfile"
packages = ["."]
pruneopts = "UT"
revision = "0ad87eef1443f64d3d8c50da647e2b1552851124"
[[projects]]
digest = "1:abcdbf03ca6ca13d3697e2186edc1f33863bbdac2b3a44dfa39015e8903f7409"
name = "github.com/olekukonko/tablewriter"
packages = ["."]
pruneopts = "UT"
revision = "e6d60cf7ba1f42d86d54cdf5508611c4aafb3970"
version = "v0.0.1"
[[projects]]
digest = "1:ee4d4af67d93cc7644157882329023ce9a7bcfce956a079069a9405521c7cc8d"
name = "github.com/opencontainers/go-digest"
packages = ["."]
pruneopts = "UT"
revision = "279bed98673dd5bef374d3b6e4b09e2af76183bf"
version = "v1.0.0-rc1"
[[projects]]
digest = "1:6eea828983c70075ca297bb915ffbcfd3e34c5a50affd94428a65df955c0ff9c"
name = "github.com/pelletier/go-toml"
packages = ["."]
pruneopts = "UT"
revision = "903d9455db9ff1d7ac1ab199062eca7266dd11a3"
version = "v1.6.0"
[[projects]]
digest = "1:7413525ee648f20b4181be7fe8103d0cb98be9e141926a03ee082dc207061e4e"
name = "github.com/phayes/freeport"
packages = ["."]
pruneopts = "UT"
revision = "b8543db493a5ed890c5499e935e2cad7504f3a04"
version = "1.0.2"
[[projects]]
digest = "1:cf31692c14422fa27c83a05292eb5cbe0fb2775972e8f1f8446a71549bd8980b"
name = "github.com/pkg/errors"
packages = ["."]
pruneopts = "UT"
revision = "ba968bfe8b2f7e042a574c888954fccecfa385b4"
version = "v0.8.1"
[[projects]]
digest = "1:bb495ec276ab82d3dd08504bbc0594a65de8c3b22c6f2aaa92d05b73fbf3a82e"
name = "github.com/spf13/afero"
packages = [
".",
"mem",
]
pruneopts = "UT"
revision = "588a75ec4f32903aa5e39a2619ba6a4631e28424"
version = "v1.2.2"
[[projects]]
digest = "1:08d65904057412fc0270fc4812a1c90c594186819243160dc779a402d4b6d0bc"
name = "github.com/spf13/cast"
packages = ["."]
pruneopts = "UT"
revision = "8c9545af88b134710ab1cd196795e7f2388358d7"
version = "v1.3.0"
[[projects]]
digest = "1:645cabccbb4fa8aab25a956cbcbdf6a6845ca736b2c64e197ca7cbb9d210b939"
name = "github.com/spf13/cobra"
packages = ["."]
pruneopts = "UT"
revision = "ef82de70bb3f60c65fb8eebacbb2d122ef517385"
version = "v0.0.3"
[[projects]]
digest = "1:1b753ec16506f5864d26a28b43703c58831255059644351bbcb019b843950900"
name = "github.com/spf13/jwalterweatherman"
packages = ["."]
pruneopts = "UT"
revision = "94f6ae3ed3bceceafa716478c5fbf8d29ca601a1"
version = "v1.1.0"
[[projects]]
digest = "1:c1b1102241e7f645bc8e0c22ae352e8f0dc6484b6cb4d132fa9f24174e0119e2"
name = "github.com/spf13/pflag"
packages = ["."]
pruneopts = "UT"
revision = "298182f68c66c05229eb03ac171abe6e309ee79a"
version = "v1.0.3"
[[projects]]
digest = "1:0b60fc944fb6a7b6c985832bd341bdb7ed8fe894fea330414e7774bb24652962"
name = "github.com/spf13/viper"
packages = ["."]
pruneopts = "UT"
revision = "72b022eb357a56469725dcd03918449e2278d02e"
version = "v1.5.0"
[[projects]]
digest = "1:f4b32291cad5efac2bfdba89ccde6aa04618b62ce06c1a571da2dc4f3f2677fb"
name = "github.com/subosito/gotenv"
packages = ["."]
pruneopts = "UT"
revision = "2ef7124db659d49edac6aa459693a15ae36c671a"
version = "v1.2.0"
[[projects]]
digest = "1:c468422f334a6b46a19448ad59aaffdfc0a36b08fdcc1c749a0b29b6453d7e59"
name = "github.com/valyala/bytebufferpool"
packages = ["."]
pruneopts = "UT"
revision = "e746df99fe4a3986f4d4f79e13c1e0117ce9c2f7"
version = "v1.0.0"
[[projects]]
digest = "1:15ad8a80098fcc7a194b9db6b26d74072a852e4faa957848c8118193d3c69230"
name = "github.com/valyala/fasthttp"
packages = [
".",
"fasthttputil",
"stackless",
]
pruneopts = "UT"
revision = "e5f51c11919d4f66400334047b897ef0a94c6f3c"
version = "v20180529"
[[projects]]
digest = "1:4c93890bbbb5016505e856cb06b5c5a2ff5b7217584d33f2a9071ebef4b5d473"
name = "go.opencensus.io"
packages = [
".",
"internal",
"internal/tagencoding",
"metric/metricdata",
"metric/metricproducer",
"plugin/ocgrpc",
"plugin/ochttp",
"plugin/ochttp/propagation/b3",
"plugin/ochttp/propagation/tracecontext",
"resource",
"stats",
"stats/internal",
"stats/view",
"tag",
"trace",
"trace/internal",
"trace/propagation",
"trace/tracestate",
]
pruneopts = "UT"
revision = "43463a80402d8447b7fce0d2c58edf1687ff0b58"
version = "v0.19.3"
[[projects]]
branch = "master"
digest = "1:bbe51412d9915d64ffaa96b51d409e070665efc5194fcf145c4a27d4133107a4"
name = "golang.org/x/crypto"
packages = ["ssh/terminal"]
pruneopts = "UT"
revision = "e1dfcc566284e143ba8f9afbb3fa563f2a0d212b"
[[projects]]
branch = "master"
digest = "1:01a2f697724170f98739b5261ec830eafc626f56b6786c730578dabcce47649c"
name = "golang.org/x/net"
packages = [
"context",
"context/ctxhttp",
"http/httpguts",
"http2",
"http2/hpack",
"idna",
"internal/socks",
"internal/timeseries",
"proxy",
"trace",
]
pruneopts = "UT"
revision = "a4d6f7feada510cc50e69a37b484cb0fdc6b7876"
[[projects]]
branch = "master"
digest = "1:645cb780e4f3177111b40588f0a7f5950efcfb473e7ff41d8d81b2ba5eaa6ed5"
name = "golang.org/x/oauth2"
packages = [
".",
"google",
"internal",
"jws",
"jwt",
]
pruneopts = "UT"
revision = "9f3314589c9a9136388751d9adae6b0ed400978a"
[[projects]]
branch = "master"
digest = "1:382bb5a7fb4034db3b6a2d19e5a4a6bcf52f4750530603c01ca18a172fa3089b"
name = "golang.org/x/sync"
packages = ["semaphore"]
pruneopts = "UT"
revision = "112230192c580c3556b8cee6403af37a4fc5f28c"
[[projects]]
branch = "master"
digest = "1:656ce95b4cdf841c00825f4cb94f6e0e1422d7d6faaf3094e94cd18884a32251"
name = "golang.org/x/sys"
packages = [
"unix",
"windows",
]
pruneopts = "UT"
revision = "a129542de9ae0895210abff9c95d67a1f33cb93d"
[[projects]]
digest = "1:8d8faad6b12a3a4c819a3f9618cb6ee1fa1cfc33253abeeea8b55336721e3405"
name = "golang.org/x/text"
packages = [
"collate",
"collate/build",
"internal/colltab",
"internal/gen",
"internal/language",
"internal/language/compact",
"internal/tag",
"internal/triegen",
"internal/ucd",
"language",
"secure/bidirule",
"transform",
"unicode/bidi",
"unicode/cldr",
"unicode/norm",
"unicode/rangetable",
]
pruneopts = "UT"
revision = "342b2e1fbaa52c93f31447ad2c6abc048c63e475"
version = "v0.3.2"
[[projects]]
branch = "master"
digest = "1:9fdc2b55e8e0fafe4b41884091e51e77344f7dc511c5acedcfd98200003bff90"
name = "golang.org/x/time"
packages = ["rate"]
pruneopts = "UT"
revision = "9d24e82272b4f38b78bc8cff74fa936d31ccd8ef"
[[projects]]
digest = "1:5f003878aabe31d7f6b842d4de32b41c46c214bb629bb485387dbcce1edf5643"
name = "google.golang.org/api"
packages = ["support/bundler"]
pruneopts = "UT"
revision = "aac82e61c0c8fe133c297b4b59316b9f481e1f0a"
version = "v0.6.0"
[[projects]]
digest = "1:04f2ff15fc59e1ddaf9900ad0e19e5b19586b31f9dafd4d592b617642b239d8f"
name = "google.golang.org/appengine"
packages = [
".",
"internal",
"internal/app_identity",
"internal/base",
"internal/datastore",
"internal/log",
"internal/modules",
"internal/remote_api",
"internal/urlfetch",
"urlfetch",
]
pruneopts = "UT"
revision = "54a98f90d1c46b7731eb8fb305d2a321c30ef610"
version = "v1.5.0"
[[projects]]
branch = "master"
digest = "1:3565a93b7692277a5dea355bc47bd6315754f3246ed07a224be6aec28972a805"
name = "google.golang.org/genproto"
packages = [
"googleapis/api/httpbody",
"googleapis/rpc/status",
"protobuf/field_mask",
]
pruneopts = "UT"
revision = "a7e196e89fd3a3c4d103ca540bd5dac3a736e375"
[[projects]]
digest = "1:e8800ddadd6bce3bc0c5ffd7bc55dbdddc6e750956c10cc10271cade542fccbe"
name = "google.golang.org/grpc"
packages = [
".",
"balancer",
"balancer/base",
"balancer/roundrobin",
"binarylog/grpc_binarylog_v1",
"codes",
"connectivity",
"credentials",
"credentials/internal",
"encoding",
"encoding/proto",
"grpclog",
"internal",
"internal/backoff",
"internal/balancerload",
"internal/binarylog",
"internal/channelz",
"internal/envconfig",
"internal/grpcrand",
"internal/grpcsync",
"internal/syscall",
"internal/transport",
"keepalive",
"metadata",
"naming",
"peer",
"resolver",
"resolver/dns",
"resolver/passthrough",
"stats",
"status",
"tap",
]
pruneopts = "UT"
revision = "501c41df7f472c740d0674ff27122f3f48c80ce7"
version = "v1.21.1"
[[projects]]
digest = "1:2d1fbdc6777e5408cabeb02bf336305e724b925ff4546ded0fa8715a7267922a"
name = "gopkg.in/inf.v0"
packages = ["."]
pruneopts = "UT"
revision = "d2d2541c53f18d2a059457998ce2876cc8e67cbf"
version = "v0.9.1"
[[projects]]
digest = "1:4d2e5a73dc1500038e504a8d78b986630e3626dc027bc030ba5c75da257cdb96"
name = "gopkg.in/yaml.v2"
packages = ["."]
pruneopts = "UT"
revision = "51d6538a90f86fe93ac480b35f37b2be17fef232"
version = "v2.2.2"
[[projects]]
digest = "1:86ad5797d1189de342ed6988fbb76b92dc0429a4d677ad69888d6137efa5712e"
name = "k8s.io/api"
packages = [
"admissionregistration/v1beta1",
"apps/v1",
"apps/v1beta1",
"apps/v1beta2",
"auditregistration/v1alpha1",
"authentication/v1",
"authentication/v1beta1",
"authorization/v1",
"authorization/v1beta1",
"autoscaling/v1",
"autoscaling/v2beta1",
"autoscaling/v2beta2",
"batch/v1",
"batch/v1beta1",
"batch/v2alpha1",
"certificates/v1beta1",
"coordination/v1",
"coordination/v1beta1",
"core/v1",
"events/v1beta1",
"extensions/v1beta1",
"networking/v1",
"networking/v1beta1",
"node/v1alpha1",
"node/v1beta1",
"policy/v1beta1",
"rbac/v1",
"rbac/v1alpha1",
"rbac/v1beta1",
"scheduling/v1",
"scheduling/v1alpha1",
"scheduling/v1beta1",
"settings/v1alpha1",
"storage/v1",
"storage/v1alpha1",
"storage/v1beta1",
]
pruneopts = "UT"
revision = "6e4e0e4f393bf5e8bbff570acd13217aa5a770cd"
version = "kubernetes-1.14.1"
[[projects]]
digest = "1:78f6a824d205c6cb0d011cce241407646b773cb57ee27e8c7e027753b4111075"
name = "k8s.io/apimachinery"
packages = [
"pkg/api/errors",
"pkg/api/meta",
"pkg/api/resource",
"pkg/apis/meta/v1",
"pkg/apis/meta/v1/unstructured",
"pkg/apis/meta/v1beta1",
"pkg/conversion",
"pkg/conversion/queryparams",
"pkg/fields",
"pkg/labels",
"pkg/runtime",
"pkg/runtime/schema",
"pkg/runtime/serializer",
"pkg/runtime/serializer/json",
"pkg/runtime/serializer/protobuf",
"pkg/runtime/serializer/recognizer",
"pkg/runtime/serializer/streaming",
"pkg/runtime/serializer/versioning",
"pkg/selection",
"pkg/types",
"pkg/util/clock",
"pkg/util/errors",
"pkg/util/framer",
"pkg/util/intstr",
"pkg/util/json",
"pkg/util/naming",
"pkg/util/net",
"pkg/util/runtime",
"pkg/util/sets",
"pkg/util/validation",
"pkg/util/validation/field",
"pkg/util/yaml",
"pkg/version",
"pkg/watch",
"third_party/forked/golang/reflect",
]
pruneopts = "UT"
revision = "6a84e37a896db9780c75367af8d2ed2bb944022e"
version = "kubernetes-1.14.1"
[[projects]]
digest = "1:37f699391265222af7da4bf8e443ca03dd834ce362fbb4b19b4d67492ff06781"
name = "k8s.io/client-go"
packages = [
"discovery",
"kubernetes",
"kubernetes/scheme",
"kubernetes/typed/admissionregistration/v1beta1",
"kubernetes/typed/apps/v1",
"kubernetes/typed/apps/v1beta1",
"kubernetes/typed/apps/v1beta2",
"kubernetes/typed/auditregistration/v1alpha1",
"kubernetes/typed/authentication/v1",
"kubernetes/typed/authentication/v1beta1",
"kubernetes/typed/authorization/v1",
"kubernetes/typed/authorization/v1beta1",
"kubernetes/typed/autoscaling/v1",
"kubernetes/typed/autoscaling/v2beta1",
"kubernetes/typed/autoscaling/v2beta2",
"kubernetes/typed/batch/v1",
"kubernetes/typed/batch/v1beta1",
"kubernetes/typed/batch/v2alpha1",
"kubernetes/typed/certificates/v1beta1",
"kubernetes/typed/coordination/v1",
"kubernetes/typed/coordination/v1beta1",
"kubernetes/typed/core/v1",
"kubernetes/typed/events/v1beta1",
"kubernetes/typed/extensions/v1beta1",
"kubernetes/typed/networking/v1",
"kubernetes/typed/networking/v1beta1",
"kubernetes/typed/node/v1alpha1",
"kubernetes/typed/node/v1beta1",
"kubernetes/typed/policy/v1beta1",
"kubernetes/typed/rbac/v1",
"kubernetes/typed/rbac/v1alpha1",
"kubernetes/typed/rbac/v1beta1",
"kubernetes/typed/scheduling/v1",
"kubernetes/typed/scheduling/v1alpha1",
"kubernetes/typed/scheduling/v1beta1",
"kubernetes/typed/settings/v1alpha1",
"kubernetes/typed/storage/v1",
"kubernetes/typed/storage/v1alpha1",
"kubernetes/typed/storage/v1beta1",
"pkg/apis/clientauthentication",
"pkg/apis/clientauthentication/v1alpha1",
"pkg/apis/clientauthentication/v1beta1",
"pkg/version",
"plugin/pkg/client/auth",
"plugin/pkg/client/auth/azure",
"plugin/pkg/client/auth/exec",
"plugin/pkg/client/auth/gcp",
"plugin/pkg/client/auth/oidc",
"plugin/pkg/client/auth/openstack",
"rest",
"rest/watch",
"third_party/forked/golang/template",
"tools/auth",
"tools/clientcmd",
"tools/clientcmd/api",
"tools/clientcmd/api/latest",
"tools/clientcmd/api/v1",
"tools/metrics",
"tools/reference",
"transport",
"util/cert",
"util/connrotation",
"util/flowcontrol",
"util/homedir",
"util/jsonpath",
"util/keyutil",
]
pruneopts = "UT"
revision = "1a26190bd76a9017e289958b9fba936430aa3704"
version = "kubernetes-1.14.1"
[[projects]]
digest = "1:c696379ad201c1e86591785579e16bf6cf886c362e9a7534e8eb0d1028b20582"
name = "k8s.io/klog"
packages = ["."]
pruneopts = "UT"
revision = "e531227889390a39d9533dde61f590fe9f4b0035"
version = "v0.3.0"
[[projects]]
branch = "master"
digest = "1:8b40227d4bf8b431fdab4f9026e6e346f00ac3be5662af367a183f78c57660b3"
name = "k8s.io/utils"
packages = ["integer"]
pruneopts = "UT"
revision = "8fab8cb257d50c8cf94ec9771e74826edbb68fb5"
[[projects]]
digest = "1:7719608fe0b52a4ece56c2dde37bedd95b938677d1ab0f84b8a7852e4c59f849"
name = "sigs.k8s.io/yaml"
packages = ["."]
pruneopts = "UT"
revision = "fd68e9863619f6ec2fdd8625fe1f02e7c877e480"
version = "v1.1.0"
[solve-meta]
analyzer-name = "dep"
analyzer-version = 1
input-imports = [
"github.com/Pallinder/sillyname-go",
"github.com/briandowns/spinner",
"github.com/dapr/dapr/pkg/components",
"github.com/dapr/dapr/pkg/config/modes",
"github.com/docker/docker/client",
"github.com/fatih/color",
"github.com/gocarina/gocsv",
"github.com/google/uuid",
"github.com/mitchellh/go-ps",
"github.com/nightlyone/lockfile",
"github.com/olekukonko/tablewriter",
"github.com/phayes/freeport",
"github.com/spf13/cobra",
"github.com/spf13/viper",
"gopkg.in/yaml.v2",
"k8s.io/api/core/v1",
"k8s.io/apimachinery/pkg/apis/meta/v1",
"k8s.io/client-go/kubernetes",
"k8s.io/client-go/plugin/pkg/client/auth",
"k8s.io/client-go/plugin/pkg/client/auth/gcp",
"k8s.io/client-go/tools/clientcmd",
]
solver-name = "gps-cdcl"
solver-version = 1

View File

@ -1,54 +0,0 @@
# Gopkg.toml example
#
# Refer to https://golang.github.io/dep/docs/Gopkg.toml.html
# for detailed Gopkg.toml documentation.
#
# required = ["github.com/user/thing/cmd/thing"]
# ignored = ["github.com/user/project/pkgX", "bitbucket.org/user/project/pkgA/pkgY"]
#
# [[constraint]]
# name = "github.com/user/project"
# version = "1.0.0"
#
# [[constraint]]
# name = "github.com/user/project2"
# branch = "dev"
# source = "github.com/myfork/project2"
#
# [[override]]
# name = "github.com/x/y"
# version = "2.4.0"
#
# [prune]
# non-go = false
# go-tests = true
# unused-packages = true
[[constraint]]
name = "github.com/fatih/color"
version = "1.7.0"
[[constraint]]
name = "github.com/spf13/cobra"
version = "0.0.3"
[[constraint]]
name = "github.com/spf13/viper"
version = "1.5.0"
[[override]]
version = "kubernetes-1.14.1"
name = "k8s.io/apimachinery"
[[override]]
version = "kubernetes-1.14.1"
name = "k8s.io/api"
[[override]]
version = "kubernetes-1.14.1"
name = "k8s.io/client-go"
[prune]
go-tests = true
unused-packages = true

View File

@ -59,6 +59,7 @@ ifeq ($(LOCAL_OS),Linux)
else ifeq ($(LOCAL_OS),Darwin)
TARGET_OS_LOCAL = darwin
GOLANGCI_LINT:=golangci-lint
PATH := $(PATH):$(HOME)/go/bin/darwin_$(GOARCH)
export ARCHIVE_EXT = .tar.gz
else
TARGET_OS_LOCAL ?= windows
@ -71,6 +72,11 @@ export BINARY_EXT ?= $(BINARY_EXT_LOCAL)
TEST_OUTPUT_FILE ?= test_output.json
# Set the default timeout for tests to 10 minutes
ifndef E2E_SH_TEST_TIMEOUT
override E2E_SH_TEST_TIMEOUT := 10m
endif
# Use the variable H to add a header (equivalent to =>) to informational output
H = $(shell printf "\033[34;1m=>\033[0m")
@ -148,7 +154,14 @@ test: test-deps
################################################################################
.PHONY: test-e2e-k8s
test-e2e-k8s: test-deps
gotestsum --jsonfile $(TEST_OUTPUT_FILE) --format standard-verbose -- -timeout 20m -count=1 -tags=e2e ./tests/e2e/kubernetes/...
gotestsum --jsonfile $(TEST_OUTPUT_FILE) --format standard-verbose -- -timeout 25m -count=1 -tags=e2e ./tests/e2e/kubernetes/...
################################################################################
# E2E Tests for K8s Template exec #
################################################################################
.PHONY: test-e2e-k8s-template
test-e2e-k8s-template: test-deps
gotestsum --jsonfile $(TEST_OUTPUT_FILE) --format standard-verbose -- -timeout 25m -count=1 -tags=templatek8s ./tests/e2e/kubernetes/...
################################################################################
# Build, E2E Tests for Kubernetes #
@ -161,7 +174,7 @@ e2e-build-run-k8s: build test-e2e-k8s
################################################################################
.PHONY: test-e2e-upgrade
test-e2e-upgrade: test-deps
gotestsum --jsonfile $(TEST_OUTPUT_FILE) --format standard-verbose -- -timeout 30m -count=1 -tags=e2e ./tests/e2e/upgrade/...
gotestsum --jsonfile $(TEST_OUTPUT_FILE) --format standard-verbose -- -timeout 60m -count=1 -tags=e2e ./tests/e2e/upgrade/...
################################################################################
# Build, E2E Tests for Kubernetes Upgrade #
@ -170,12 +183,19 @@ test-e2e-upgrade: test-deps
e2e-build-run-upgrade: build test-e2e-upgrade
################################################################################
# E2E Tests for Self-Hosted Template exec #
################################################################################
.PHONY: test-e2e-sh-template
test-e2e-sh-template: test-deps
gotestsum --jsonfile $(TEST_OUTPUT_FILE) --format standard-verbose -- -timeout $(E2E_SH_TEST_TIMEOUT) -count=1 -tags=template ./tests/e2e/standalone/...
################################################################################
# E2E Tests for Self-Hosted #
################################################################################
.PHONY: test-e2e-sh
test-e2e-sh: test-deps
gotestsum --jsonfile $(TEST_OUTPUT_FILE) --format standard-verbose -- -count=1 -tags=e2e ./tests/e2e/standalone/...
gotestsum --jsonfile $(TEST_OUTPUT_FILE) --format standard-verbose -- -timeout $(E2E_SH_TEST_TIMEOUT) -count=1 -tags=e2e ./tests/e2e/standalone/...
################################################################################
# Build, E2E Tests for Self-Hosted #
@ -188,7 +208,7 @@ e2e-build-run-sh: build test-e2e-sh
################################################################################
.PHONY: modtidy
modtidy:
go mod tidy -compat=1.19
go mod tidy -compat=1.21
################################################################################
# Target: check-diff #
@ -196,3 +216,12 @@ modtidy:
.PHONY: check-diff
check-diff:
git diff --exit-code ./go.mod # check no changes
################################################################################
# Target: vuln-check #
################################################################################
.PHONY: vuln-check
vuln-check:
@echo "Checking for vulnerabilities..."
go install golang.org/x/vuln/cmd/govulncheck@latest
govulncheck ./...

View File

@ -68,7 +68,7 @@ Install windows Dapr CLI using MSI package.
### Install Dapr on your local machine (self-hosted)
In self-hosted mode, dapr can be initialized using the CLI with the placement, redis and zipkin containers enabled by default(recommended) or without them which also does not require docker to be available in the environment.
In self-hosted mode, dapr can be initialized using the CLI with the placement, scheduler, redis, and zipkin containers enabled by default(recommended) or without them which also does not require docker to be available in the environment.
#### Initialize Dapr
@ -89,17 +89,18 @@ Output should look like so:
✅ Downloaded binaries and completed components set up.
daprd binary has been installed to $HOME/.dapr/bin.
dapr_placement container is running.
dapr_scheduler container is running.
dapr_redis container is running.
dapr_zipkin container is running.
Use `docker ps` to check running containers.
✅ Success! Dapr is up and running. To get started, go here: https://aka.ms/dapr-getting-started
✅ Success! Dapr is up and running. To get started, go here: https://docs.dapr.io/getting-started
```
> Note: To see that Dapr has been installed successfully, from a command prompt run the `docker ps` command and check that the `daprio/dapr:latest`, `dapr_redis` and `dapr_zipkin` container images are all running.
This step creates the following defaults:
1. components folder which is later used during `dapr run` unless the `--components-path` option is provided. For Linux/MacOS, the default components folder path is `$HOME/.dapr/components` and for Windows it is `%USERPROFILE%\.dapr\components`.
1. components folder which is later used during `dapr run` unless the `--resources-path` (`--components-path` is deprecated and will be removed in future releases) option is provided. For Linux/MacOS, the default components folder path is `$HOME/.dapr/components` and for Windows it is `%USERPROFILE%\.dapr\components`.
2. component files in the components folder called `pubsub.yaml` and `statestore.yaml`.
3. default config file `$HOME/.dapr/config.yaml` for Linux/MacOS or for Windows at `%USERPROFILE%\.dapr\config.yaml` to enable tracing on `dapr init` call. Can be overridden with the `--config` flag on `dapr run`.
@ -118,10 +119,11 @@ Output should look like so:
✅ Downloaded binaries and completed components set up.
daprd binary has been installed to $HOME/.dapr/bin.
placement binary has been installed.
✅ Success! Dapr is up and running. To get started, go here: https://aka.ms/dapr-getting-started
scheduler binary has been installed.
✅ Success! Dapr is up and running. To get started, go here: https://docs.dapr.io/getting-started
```
>Note: When initializing Dapr with the `--slim` flag only the Dapr runtime binary and the placement service binary are installed. An empty default components folder is created with no default configuration files. During `dapr run` user should use `--components-path` to point to a components directory with custom configurations files or alternatively place these files in the default directory. For Linux/MacOS, the default components directory path is `$HOME/.dapr/components` and for Windows it is `%USERPROFILE%\.dapr\components`.
>Note: When initializing Dapr with the `--slim` flag only the Dapr runtime, placement, and scheduler service binaries are installed. An empty default components folder is created with no default configuration files. During `dapr run` user should use `--resources-path` (`--components-path` is deprecated and will be removed in future releases) to point to a components directory with custom configurations files or alternatively place these files in the default directory. For Linux/MacOS, the default components directory path is `$HOME/.dapr/components` and for Windows it is `%USERPROFILE%\.dapr\components`.
#### Install a specific runtime version
@ -139,7 +141,7 @@ Runtime version: v1.0.0
#### Install with mariner images
You can install Dapr Runtime using mariner images using the `--image-variant` flag.
You can install Dapr Runtime using mariner images using the `--image-variant` flag.
```bash
# Installing Dapr with Mariner images
@ -156,6 +158,17 @@ You can install Dapr runtime by pulling docker images from a given private regis
dapr init --image-registry example.io/<username>
```
#### Install with a custom scheduler host and port
You can install Dapr runtime with a custom scheduler host and port by using `--scheduler-override-broadcast-host-port` flag.
```bash
dapr init --scheduler-override-broadcast-host-port 192.168.42.42:50006
```
> Note: The default host is `localhost`.
#### Install in airgap environment
You can install Dapr runtime in airgap (offline) environment using a pre-downloaded [installer bundle](https://github.com/dapr/installer-bundle/releases). You need to download the archived bundle for your OS beforehand (e.g., daprbundle_linux_amd64.tar.gz,) and unpack it. Thereafter use the local Dapr CLI binary in the bundle with `--from-dir` flag in the init command to point to the extracted bundle location to initialize Dapr.
@ -171,14 +184,14 @@ Move to the bundle directory and run the following command:
> If you are not running the above command from the bundle directory, provide the full path to bundle directory as input. For example, assuming the bundle directory path is $HOME/daprbundle, run `$HOME/daprbundle/dapr init --from-dir $HOME/daprbundle` to have the same behavior.
> Note: Dapr Installer bundle just contains the placement container apart from the binaries and so `zipkin` and `redis` are not enabled by default. You can pull the images locally either from network or private registry and run as follows:
> Note: Dapr Installer bundle just contains the placement and scheduler containers apart from the binaries and so `zipkin` and `redis` are not enabled by default. You can pull the images locally either from network or private registry and run as follows:
```bash
docker run --name "dapr_zipkin" --restart always -d -p 9411:9411 openzipkin/zipkin
docker run --name "dapr_redis" --restart always -d -p 6379:6379 redis
```
Alternatively to the above, you can also have slim installation as well to install dapr without running any Docker containers in airgap mode.
Alternatively to the above, you can also have slim installation as well to install dapr without running any Docker containers in airgap mode.
```bash
./dapr init --slim --from-dir .
@ -199,6 +212,9 @@ dapr init --network dapr-network
> Note: When installed to a specific Docker network, you will need to add the `--placement-host-address` arguments to `dapr run` commands run in any containers within that network.
> The format of `--placement-host-address` argument is either `<hostname>` or `<hostname>:<port>`. If the port is omitted, the default port `6050` for Windows and `50005` for Linux/MacOS applies.
> Note: When installed to a specific Docker network, you will need to add the `--scheduler-host-address` arguments to `dapr run` commands run in any containers within that network.
> The format of `--scheduler-host-address` argument is either `<hostname>` or `<hostname>:<port>`. If the port is omitted, the default port `6060` for Windows and `50006` for Linux/MacOS applies.
#### Install with a specific container runtime
You can install the Dapr runtime using a specific container runtime
@ -212,9 +228,23 @@ $ dapr init --container-runtime podman
> Note: The default container runtime is Docker.
#### In a dev container or GitHub Codespace
To install the Dapr CLI in a dev container or GitHub Codespace, add the following to your `devcontainer.json` file:
```jsonc
"features": {
"ghcr.io/dapr/cli/dapr-cli:0": {}
}
```
Restart your dev container or GitHub Codespace and run `dapr init` to initialize Dapr.
For more details, see the docs for dev containers with [Visual Studio Code](https://code.visualstudio.com/docs/devcontainers/containers#_dev-container-features) and [GitHub Codespaces](https://docs.github.com/en/codespaces/setting-up-your-project-for-codespaces/configuring-dev-containers/adding-features-to-a-devcontainer-file).
### Uninstall Dapr in a standalone mode
Uninstalling will remove daprd binary and the placement container (if installed with Docker or the placement binary if not).
Uninstalling will remove daprd binary along with the placement and scheduler containers (if installed with Docker or the placement and scheduler binaries if not).
```bash
@ -223,7 +253,7 @@ dapr uninstall
> For Linux users, if you run your docker cmds with sudo, you need to use "**sudo dapr uninstall**" to remove the containers.
The command above won't remove the redis or zipkin containers by default in case you were using it for other purposes. It will also not remove the default dapr folder that was created on `dapr init`. To remove all the containers (placement, redis, zipkin) and also the default dapr folder created on init run:
The command above won't remove the redis or zipkin containers by default in case you were using it for other purposes. It will also not remove the default dapr folder that was created on `dapr init`. To remove all the containers (placement, scheduler, redis, zipkin) and also the default dapr folder created on init run:
```bash
dapr uninstall --all
@ -231,7 +261,7 @@ dapr uninstall --all
The above command can also be run when Dapr has been installed in a non-docker environment, it will only remove the installed binaries and the default dapr folder in that case.
> NB: The `dapr uninstall` command will always try to remove the placement binary/service and will throw an error is not able to.
> NB: The `dapr uninstall` command will always try to remove the placement and scheduler binaries/services and will throw an error is not able to.
**You should always run a `dapr uninstall` before running another `dapr init`.**
@ -270,7 +300,7 @@ Output should look like as follows:
Note: To install Dapr using Helm, see here: https://docs.dapr.io/getting-started/install-dapr/#install-with-helm-advanced
✅ Deploying the Dapr control plane to your cluster...
✅ Success! Dapr has been installed to namespace dapr-system. To verify, run "dapr status -k" in your terminal. To get started, go here: https://aka.ms/dapr-getting-started
✅ Success! Dapr has been installed to namespace dapr-system. To verify, run "dapr status -k" in your terminal. To get started, go here: https://docs.dapr.io/getting-started
```
#### Supplying Helm values
@ -278,7 +308,7 @@ Output should look like as follows:
All available [Helm Chart values](https://github.com/dapr/dapr/tree/master/charts/dapr#configuration) can be set by using the `--set` flag:
```bash
dapr init -k --set global.tag=1.0.0 --set dapr_operator.logLevel=error
dapr init -k --set global.tag=1.0.0 --set dapr_operator.logLevel=error
```
#### Installing to a custom namespace
@ -337,12 +367,14 @@ dapr upgrade -k --runtime-version=1.0.0
The example above shows how to upgrade from your current version to version `1.0.0`.
*Note: `dapr upgrade` will retry up to 5 times upon failure*
#### Supplying Helm values
All available [Helm Chart values](https://github.com/dapr/dapr/tree/master/charts/dapr#configuration) can be set by using the `--set` flag:
```bash
dapr upgrade -k --runtime-version=1.0.0 --set global.tag=my-tag --set dapr_operator.logLevel=error
dapr upgrade -k --runtime-version=1.0.0 --set global.tag=my-tag --set dapr_operator.logLevel=error
```
*Note: do not use the `dapr upgrade` command if you're upgrading from 0.x versions of Dapr*
@ -391,7 +423,7 @@ dapr init --network dapr-network
dapr run --app-id nodeapp --placement-host-address dapr_placement node app.js
```
> Note: When in a specific Docker network, the Redis, Zipkin and placement service containers are given specific network aliases, `dapr_redis`, `dapr_zipkin` and `dapr_placement`, respectively. The default configuration files reflect the network alias rather than `localhost` when a docker network is specified.
> Note: When in a specific Docker network, the Redis, Zipkin and placement and scheduler service containers are given specific network aliases, `dapr_redis`, `dapr_zipkin`, `dapr_placement`, and `dapr_scheduler`, respectively. The default configuration files reflect the network alias rather than `localhost` when a docker network is specified.
### Use gRPC
@ -444,7 +476,7 @@ Launch Dapr and your app:
dapr run --app-id nodeapp --app-port 3000 node app.js
```
Note: To choose a non-default components folder, use the --components-path option.
Note: To choose a non-default components folder, use the --resources-path(--components-path is deprecated) option.
Invoke your app:
@ -537,6 +569,10 @@ Use user provided ca.crt, issuer.crt and issuer.key
```bash
dapr mtls renew-certificate -k --ca-root-certificate <ca.crt> --issuer-private-key <issuer.key> --issuer-public-certificate <issuer.crt> --restart
```
#### To view the complete list of flags and their combination, run below command:
```bash
dapr mtls renew-certificate -h
```
### List Components
@ -557,7 +593,8 @@ dapr components --kubernetes --namespace target-namespace
To use a custom path for component definitions
```bash
dapr run --components-path [custom path]
dapr run --resources-path [custom path]
> Note: --components-path flag is deprecated. It will continue to work until it is removed completely.
```
@ -723,7 +760,9 @@ See the [Reference Guide](https://docs.dapr.io/reference/cli/) for more informat
## Contributing to Dapr CLI
See the [Development Guide](https://github.com/dapr/cli/blob/master/docs/development/development.md) to get started with building and developing.
## Release process for Dapr CLI
See the [Release Guide](https://github.com/dapr/cli/blob/master/docs/development/release.md) for complete release process for Dapr CLI.
## Code of Conduct
Please refer to our [Dapr Community Code of Conduct](https://github.com/dapr/community/blob/master/CODE-OF-CONDUCT.md)

View File

@ -21,6 +21,11 @@ import (
"net/url"
"os"
"path/filepath"
"strconv"
"github.com/dapr/dapr/pkg/runtime"
"k8s.io/apimachinery/pkg/api/resource"
"github.com/spf13/cobra"
@ -60,8 +65,8 @@ var (
annotateReadinessProbeThreshold int
annotateDaprImage string
annotateAppSSL bool
annotateMaxRequestBodySize int
annotateReadBufferSize int
annotateMaxRequestBodySize string
annotateReadBufferSize string
annotateHTTPStreamRequestBody bool
annotateGracefulShutdownSeconds int
annotateEnableAPILogging bool
@ -221,7 +226,6 @@ func readInputsFromFS(path string) ([]io.Reader, error) {
inputs = append(inputs, file)
return nil
})
if err != nil {
return nil, err
}
@ -319,12 +323,23 @@ func getOptionsFromFlags() kubernetes.AnnotateOptions {
if annotateAppSSL {
o = append(o, kubernetes.WithAppSSL())
}
if annotateMaxRequestBodySize != -1 {
o = append(o, kubernetes.WithMaxRequestBodySize(annotateMaxRequestBodySize))
if annotateMaxRequestBodySize != "-1" {
if q, err := resource.ParseQuantity(annotateMaxRequestBodySize); err != nil {
print.FailureStatusEvent(os.Stderr, "error parsing value of max-body-size: %s, error: %s", annotateMaxRequestBodySize, err.Error())
os.Exit(1)
} else {
o = append(o, kubernetes.WithMaxRequestBodySize(int(q.Value())))
}
}
if annotateReadBufferSize != -1 {
o = append(o, kubernetes.WithReadBufferSize(annotateReadBufferSize))
if annotateReadBufferSize != "-1" {
if q, err := resource.ParseQuantity(annotateReadBufferSize); err != nil {
print.FailureStatusEvent(os.Stderr, "error parsing value of read-buffer-size: %s, error: %s", annotateMaxRequestBodySize, err.Error())
os.Exit(1)
} else {
o = append(o, kubernetes.WithReadBufferSize(int(q.Value())))
}
}
if annotateHTTPStreamRequestBody {
o = append(o, kubernetes.WithHTTPStreamRequestBody())
}
@ -359,7 +374,7 @@ func init() {
AnnotateCmd.Flags().StringVarP(&annotateAppID, "app-id", "a", "", "The app id to annotate")
AnnotateCmd.Flags().IntVarP(&annotateAppPort, "app-port", "p", -1, "The port to expose the app on")
AnnotateCmd.Flags().StringVarP(&annotateConfig, "config", "c", "", "The config file to annotate")
AnnotateCmd.Flags().StringVar(&annotateAppProtocol, "app-protocol", "", "The protocol to use for the app")
AnnotateCmd.Flags().StringVar(&annotateAppProtocol, "app-protocol", "", "The protocol to use for the app. Allowed values http, https, h2c, grpc, grpcs")
AnnotateCmd.Flags().BoolVar(&annotateEnableProfile, "enable-profile", false, "Enable profiling")
AnnotateCmd.Flags().StringVar(&annotateLogLevel, "log-level", "", "The log level to use")
AnnotateCmd.Flags().StringVar(&annotateAPITokenSecret, "api-token-secret", "", "The secret to use for the API token")
@ -385,8 +400,9 @@ func init() {
AnnotateCmd.Flags().IntVar(&annotateReadinessProbeThreshold, "readiness-probe-threshold", -1, "The threshold to use for the readiness probe")
AnnotateCmd.Flags().StringVar(&annotateDaprImage, "dapr-image", "", "The image to use for the dapr sidecar container")
AnnotateCmd.Flags().BoolVar(&annotateAppSSL, "app-ssl", false, "Enable SSL for the app")
AnnotateCmd.Flags().IntVar(&annotateMaxRequestBodySize, "max-request-body-size", -1, "The maximum request body size to use")
AnnotateCmd.Flags().IntVar(&annotateReadBufferSize, "http-read-buffer-size", -1, "The maximum size of HTTP header read buffer in kilobytes")
AnnotateCmd.Flags().MarkDeprecated("app-ssl", "This flag is deprecated and will be removed in a future release. Use \"app-protocol\" flag with https or grpcs instead")
AnnotateCmd.Flags().StringVar(&annotateMaxRequestBodySize, "max-body-size", strconv.Itoa(runtime.DefaultMaxRequestBodySize>>20)+"Mi", "The maximum request body size to use")
AnnotateCmd.Flags().StringVar(&annotateReadBufferSize, "read-buffer-size", strconv.Itoa(runtime.DefaultReadBufferSize>>10)+"Ki", "The maximum size of HTTP header read buffer in kilobytes")
AnnotateCmd.Flags().BoolVar(&annotateHTTPStreamRequestBody, "http-stream-request-body", false, "Enable streaming request body for HTTP")
AnnotateCmd.Flags().IntVar(&annotateGracefulShutdownSeconds, "graceful-shutdown-seconds", -1, "The number of seconds to wait for the app to shutdown")
AnnotateCmd.Flags().BoolVar(&annotateEnableAPILogging, "enable-api-logging", false, "Enable API logging for the Dapr sidecar")

View File

@ -15,9 +15,11 @@ package cmd
import (
"fmt"
"os"
"github.com/spf13/cobra"
"github.com/dapr/cli/pkg/print"
"github.com/dapr/cli/pkg/standalone"
)
@ -29,7 +31,12 @@ var BuildInfoCmd = &cobra.Command{
dapr build-info
`,
Run: func(cmd *cobra.Command, args []string) {
fmt.Println(standalone.GetBuildInfo(RootCmd.Version))
out, err := standalone.GetBuildInfo(daprRuntimePath, cliVersion)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Error getting build info: %s", err.Error())
os.Exit(1)
}
fmt.Println(out)
},
}

View File

@ -57,6 +57,12 @@ var completionExample = `
# Set the dapr completion code for zsh[1] to autoload on startup
dapr completion zsh > "${fpath[1]}/_dapr"
# Installing fish completion on Linux
## Load the dapr completion code for fish into the current shell
dapr completion fish | source
# Set the dapr completion code for fish[1] to autoload on startup
dapr completion fish > $HOME/.config/fish/completions/dapr.fish
# Installing powershell completion on Windows
## Create $PROFILE if it not exists
if (!(Test-Path -Path $PROFILE )){ New-Item -Type File -Path $PROFILE -Force }
@ -77,6 +83,7 @@ func newCompletionCmd() *cobra.Command {
cmd.AddCommand(
newCompletionBashCmd(),
newCompletionZshCmd(),
newCompletionFishCmd(),
newCompletionPowerShellCmd(),
)
@ -112,6 +119,19 @@ func newCompletionZshCmd() *cobra.Command {
return cmd
}
func newCompletionFishCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "fish",
Short: "Generates fish completion scripts",
Run: func(cmd *cobra.Command, args []string) {
RootCmd.GenFishCompletion(os.Stdout, true)
},
}
cmd.Flags().BoolP("help", "h", false, "Print this help message")
return cmd
}
func newCompletionPowerShellCmd() *cobra.Command {
cmd := &cobra.Command{
Use: "powershell",

View File

@ -30,15 +30,22 @@ var RootCmd = &cobra.Command{
Use: "dapr",
Short: "Dapr CLI",
Long: `
__
__
____/ /___ _____ _____
/ __ / __ '/ __ \/ ___/
/ /_/ / /_/ / /_/ / /
\__,_/\__,_/ .___/_/
/_/
/ /_/ / /_/ / /_/ / /
\__,_/\__,_/ .___/_/
/_/
===============================
Distributed Application Runtime`,
Run: func(cmd *cobra.Command, _ []string) {
if versionFlag {
printVersion()
} else {
cmd.Help()
}
},
}
type daprVersion struct {
@ -46,40 +53,51 @@ type daprVersion struct {
RuntimeVersion string `json:"Runtime version"`
}
type osType string
const (
windowsOsType osType = "windows"
)
var (
daprVer daprVersion
logAsJSON bool
cliVersion string
versionFlag bool
daprVer daprVersion
logAsJSON bool
daprRuntimePath string
)
// Execute adds all child commands to the root command.
func Execute(version, apiVersion string) {
RootCmd.Version = version
// Need to be set here as it is accessed in initConfig.
cliVersion = version
api.RuntimeAPIVersion = apiVersion
daprVer = daprVersion{
CliVersion: version,
RuntimeVersion: strings.ReplaceAll(standalone.GetRuntimeVersion(), "\n", ""),
}
cobra.OnInitialize(initConfig)
setVersion()
if err := RootCmd.Execute(); err != nil {
fmt.Println(err)
os.Exit(-1)
}
}
func setVersion() {
template := fmt.Sprintf(cliVersionTemplateString, daprVer.CliVersion, daprVer.RuntimeVersion)
RootCmd.SetVersionTemplate(template)
func printVersion() {
fmt.Printf(cliVersionTemplateString, daprVer.CliVersion, daprVer.RuntimeVersion)
}
// Function is called as a preRun initializer for each command executed.
func initConfig() {
if logAsJSON {
print.EnableJSONFormat()
}
// err intentionally ignored since daprd may not yet be installed.
runtimeVer, _ := standalone.GetRuntimeVersion(daprRuntimePath)
daprVer = daprVersion{
// Set in Execute() method in this file before initConfig() is called by cmd.Execute().
CliVersion: cliVersion,
RuntimeVersion: strings.ReplaceAll(runtimeVer, "\n", ""),
}
viper.SetEnvPrefix("dapr")
viper.SetEnvKeyReplacer(strings.NewReplacer("-", "_"))
@ -87,5 +105,7 @@ func initConfig() {
}
func init() {
RootCmd.Flags().BoolVarP(&versionFlag, "version", "v", false, "version for dapr")
RootCmd.PersistentFlags().StringVarP(&daprRuntimePath, "runtime-path", "", "", "The path to the dapr runtime installation directory")
RootCmd.PersistentFlags().BoolVarP(&logAsJSON, "log-as-json", "", false, "Log output in JSON format")
}

View File

@ -18,6 +18,7 @@ import (
"net"
"os"
"os/signal"
"strconv"
"github.com/pkg/browser"
"github.com/spf13/cobra"
@ -62,11 +63,14 @@ var DashboardCmd = &cobra.Command{
# Start dashboard locally
dapr dashboard
# Start dashboard locally in a specified port
# Start dashboard locally in a specified port
dapr dashboard -p 9999
# Port forward to dashboard in Kubernetes
dapr dashboard -k
# Start dashboard locally on a random port which is free.
dapr dashboard -p 0
# Port forward to dashboard in Kubernetes
dapr dashboard -k
# Port forward to dashboard in Kubernetes on all addresses in a specified port
dapr dashboard -k -p 9999 -a 0.0.0.0
@ -79,7 +83,13 @@ dapr dashboard -k -p 0
`,
Run: func(cmd *cobra.Command, args []string) {
if dashboardVersionCmd {
fmt.Println(standalone.GetDashboardVersion())
dashboardVer, err := standalone.GetDashboardVersion(daprRuntimePath)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Failed to get Dapr install directory: %v", err)
os.Exit(1)
}
fmt.Println(dashboardVer)
os.Exit(0)
}
@ -93,6 +103,12 @@ dapr dashboard -k -p 0
os.Exit(1)
}
if err := utils.CheckIfPortAvailable(dashboardLocalPort); err != nil {
print.FailureStatusEvent(os.Stderr, "Please select a different port with %q flag: %s", "-p", err)
print.InfoStatusEvent(os.Stdout, "You can also use port 0 to select a random free port.")
os.Exit(1)
}
if kubernetesMode {
config, client, err := kubernetes.GetKubeConfigClient()
if err != nil {
@ -165,9 +181,9 @@ dapr dashboard -k -p 0
}()
// url for dashboard after port forwarding.
var webURL string = net.JoinHostPort(dashboardHost, fmt.Sprint(portForward.LocalPort))
webURL := "http://" + net.JoinHostPort(dashboardHost, strconv.Itoa(portForward.LocalPort))
print.InfoStatusEvent(os.Stdout, fmt.Sprintf("Dapr dashboard found in namespace:\t%s", foundNamespace))
print.InfoStatusEvent(os.Stdout, "Dapr dashboard found in namespace:\t"+foundNamespace)
print.InfoStatusEvent(os.Stdout, fmt.Sprintf("Dapr dashboard available at:\t%s\n", webURL))
err = browser.OpenURL(webURL)
@ -179,9 +195,14 @@ dapr dashboard -k -p 0
<-portForward.GetStop()
} else {
// Standalone mode.
err := standalone.NewDashboardCmd(dashboardLocalPort).Run()
dashboardCmd, err := standalone.NewDashboardCmd(daprRuntimePath, dashboardLocalPort)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Dapr dashboard not found. Is Dapr installed?")
print.FailureStatusEvent(os.Stderr, "Failed to get Dapr install directory: %v", err)
} else {
err = dashboardCmd.Run()
if err != nil {
print.FailureStatusEvent(os.Stderr, "Dapr dashboard failed to run: %v", err)
}
}
}
},
@ -199,5 +220,6 @@ func init() {
DashboardCmd.Flags().IntVarP(&dashboardLocalPort, "port", "p", defaultLocalPort, "The local port on which to serve Dapr dashboard")
DashboardCmd.Flags().StringVarP(&dashboardNamespace, "namespace", "n", daprSystemNamespace, "The namespace where Dapr dashboard is running")
DashboardCmd.Flags().BoolP("help", "h", false, "Print this help message")
RootCmd.AddCommand(DashboardCmd)
}

View File

@ -14,6 +14,7 @@ limitations under the License.
package cmd
import (
"errors"
"fmt"
"os"
"strings"
@ -24,24 +25,28 @@ import (
"github.com/dapr/cli/pkg/kubernetes"
"github.com/dapr/cli/pkg/print"
"github.com/dapr/cli/pkg/standalone"
"github.com/dapr/cli/utils"
)
var (
kubernetesMode bool
wait bool
timeout uint
slimMode bool
runtimeVersion string
dashboardVersion string
allNamespaces bool
initNamespace string
resourceNamespace string
enableMTLS bool
enableHA bool
values []string
fromDir string
containerRuntime string
imageVariant string
kubernetesMode bool
wait bool
timeout uint
slimMode bool
devMode bool
runtimeVersion string
dashboardVersion string
allNamespaces bool
initNamespace string
resourceNamespace string
enableMTLS bool
enableHA bool
values []string
fromDir string
containerRuntime string
imageVariant string
schedulerVolume string
schedulerOverrideBroadcastHostPort string
)
var InitCmd = &cobra.Command{
@ -50,18 +55,25 @@ var InitCmd = &cobra.Command{
PreRun: func(cmd *cobra.Command, args []string) {
viper.BindPFlag("network", cmd.Flags().Lookup("network"))
viper.BindPFlag("image-registry", cmd.Flags().Lookup("image-registry"))
runtimeVersion = getConfigurationValue("runtime-version", cmd)
dashboardVersion = getConfigurationValue("dashboard-version", cmd)
containerRuntime = getConfigurationValue("container-runtime", cmd)
},
Example: `
# Initialize Dapr in self-hosted mode
dapr init
# Initialize Dapr in self-hosted mode with a provided docker image registry. Image looked up as <registry-url>/<image>.
# Check docs or README for more information on the format of the image path that is required.
# Check docs or README for more information on the format of the image path that is required.
dapr init --image-registry <registry-url>
# Initialize Dapr in Kubernetes
dapr init -k
# Initialize Dapr in Kubernetes in dev mode
dapr init -k --dev
# Initialize Dapr in Kubernetes and wait for the installation to complete (default timeout is 300s/5m)
dapr init -k --wait --timeout 600
@ -80,6 +92,10 @@ dapr init --from-dir <path-to-directory>
# Initialize dapr with a particular image variant. Allowed values: "mariner"
dapr init --image-variant <variant>
# Initialize Dapr inside a ".dapr" directory present in a non-default location
# Folder .dapr will be created in folder pointed to by <path-to-install-directory>
dapr init --runtime-path <path-to-install-directory>
# See more at: https://docs.dapr.io/getting-started/
`,
Run: func(cmd *cobra.Command, args []string) {
@ -91,6 +107,11 @@ dapr init --image-variant <variant>
imageRegistryURI := ""
var err error
if len(strings.TrimSpace(daprRuntimePath)) != 0 {
print.FailureStatusEvent(os.Stderr, "--runtime-path is only valid for self-hosted mode")
os.Exit(1)
}
if len(imageRegistryFlag) != 0 {
warnForPrivateRegFeat()
imageRegistryURI = imageRegistryFlag
@ -101,23 +122,33 @@ dapr init --image-variant <variant>
print.FailureStatusEvent(os.Stderr, err.Error())
os.Exit(1)
}
if err = verifyCustomCertFlags(cmd); err != nil {
print.FailureStatusEvent(os.Stderr, err.Error())
os.Exit(1)
}
config := kubernetes.InitConfiguration{
Namespace: initNamespace,
Version: runtimeVersion,
EnableMTLS: enableMTLS,
EnableHA: enableHA,
Args: values,
Wait: wait,
Timeout: timeout,
ImageRegistryURI: imageRegistryURI,
ImageVariant: imageVariant,
Namespace: initNamespace,
Version: runtimeVersion,
DashboardVersion: dashboardVersion,
EnableMTLS: enableMTLS,
EnableHA: enableHA,
EnableDev: devMode,
Args: values,
Wait: wait,
Timeout: timeout,
ImageRegistryURI: imageRegistryURI,
ImageVariant: imageVariant,
RootCertificateFilePath: strings.TrimSpace(caRootCertificateFile),
IssuerCertificateFilePath: strings.TrimSpace(issuerPublicCertificateFile),
IssuerPrivateKeyFilePath: strings.TrimSpace(issuerPrivateKeyFile),
}
err = kubernetes.Init(config)
if err != nil {
print.FailureStatusEvent(os.Stderr, err.Error())
os.Exit(1)
}
print.SuccessStatusEvent(os.Stdout, fmt.Sprintf("Success! Dapr has been installed to namespace %s. To verify, run `dapr status -k' in your terminal. To get started, go here: https://aka.ms/dapr-getting-started", config.Namespace))
print.SuccessStatusEvent(os.Stdout, fmt.Sprintf("Success! Dapr has been installed to namespace %s. To verify, run `dapr status -k' in your terminal. To get started, go here: https://docs.dapr.io/getting-started", config.Namespace))
} else {
dockerNetwork := ""
imageRegistryURI := ""
@ -136,48 +167,88 @@ dapr init --image-variant <variant>
if len(imageRegistryURI) != 0 {
warnForPrivateRegFeat()
}
err := standalone.Init(runtimeVersion, dashboardVersion, dockerNetwork, slimMode, imageRegistryURI, fromDir, containerRuntime, imageVariant)
if !utils.IsValidContainerRuntime(containerRuntime) {
print.FailureStatusEvent(os.Stdout, "Invalid container runtime. Supported values are docker and podman.")
os.Exit(1)
}
schedulerHostPort := &schedulerOverrideBroadcastHostPort
if schedulerOverrideBroadcastHostPort == "" {
schedulerHostPort = nil
}
err := standalone.Init(runtimeVersion, dashboardVersion, dockerNetwork, slimMode, imageRegistryURI, fromDir, containerRuntime, imageVariant, daprRuntimePath, &schedulerVolume, schedulerHostPort)
if err != nil {
print.FailureStatusEvent(os.Stderr, err.Error())
os.Exit(1)
}
print.SuccessStatusEvent(os.Stdout, "Success! Dapr is up and running. To get started, go here: https://aka.ms/dapr-getting-started")
print.SuccessStatusEvent(os.Stdout, "Success! Dapr is up and running. To get started, go here: https://docs.dapr.io/getting-started")
}
},
}
func verifyCustomCertFlags(cmd *cobra.Command) error {
ca := cmd.Flags().Lookup("ca-root-certificate")
issuerKey := cmd.Flags().Lookup("issuer-private-key")
issuerCert := cmd.Flags().Lookup("issuer-public-certificate")
if ca.Changed && len(strings.TrimSpace(ca.Value.String())) == 0 {
return errors.New("non empty value of --ca-root-certificate must be provided")
}
if issuerKey.Changed && len(strings.TrimSpace(issuerKey.Value.String())) == 0 {
return errors.New("non empty value of --issuer-private-key must be provided")
}
if issuerCert.Changed && len(strings.TrimSpace(issuerCert.Value.String())) == 0 {
return errors.New("non empty value of --issuer-public-certificate must be provided")
}
return nil
}
func warnForPrivateRegFeat() {
print.WarningStatusEvent(os.Stdout, "Flag --image-registry is a preview feature and is subject to change.")
}
func init() {
defaultRuntimeVersion := "latest"
viper.BindEnv("runtime_version_override", "DAPR_RUNTIME_VERSION")
runtimeVersionEnv := viper.GetString("runtime_version_override")
if runtimeVersionEnv != "" {
defaultRuntimeVersion = runtimeVersionEnv
}
defaultDashboardVersion := "latest"
viper.BindEnv("dashboard_version_override", "DAPR_DASHBOARD_VERSION")
dashboardVersionEnv := viper.GetString("dashboard_version_override")
if dashboardVersionEnv != "" {
defaultDashboardVersion = dashboardVersionEnv
}
defaultContainerRuntime := string(utils.DOCKER)
InitCmd.Flags().BoolVarP(&kubernetesMode, "kubernetes", "k", false, "Deploy Dapr to a Kubernetes cluster")
InitCmd.Flags().BoolVarP(&devMode, "dev", "", false, "Use Dev mode. Deploy Redis, Zipkin also in the Kubernetes cluster")
InitCmd.Flags().BoolVarP(&wait, "wait", "", false, "Wait for Kubernetes initialization to complete")
InitCmd.Flags().UintVarP(&timeout, "timeout", "", 300, "The wait timeout for the Kubernetes installation")
InitCmd.Flags().BoolVarP(&slimMode, "slim", "s", false, "Exclude placement service, Redis and Zipkin containers from self-hosted installation")
InitCmd.Flags().BoolVarP(&slimMode, "slim", "s", false, "Exclude placement service, scheduler service, Redis and Zipkin containers from self-hosted installation")
InitCmd.Flags().StringVarP(&runtimeVersion, "runtime-version", "", defaultRuntimeVersion, "The version of the Dapr runtime to install, for example: 1.0.0")
InitCmd.Flags().StringVarP(&dashboardVersion, "dashboard-version", "", defaultDashboardVersion, "The version of the Dapr dashboard to install, for example: 1.0.0")
InitCmd.Flags().StringVarP(&dashboardVersion, "dashboard-version", "", defaultDashboardVersion, "The version of the Dapr dashboard to install, for example: 0.13.0")
InitCmd.Flags().StringVarP(&initNamespace, "namespace", "n", "dapr-system", "The Kubernetes namespace to install Dapr in")
InitCmd.Flags().BoolVarP(&enableMTLS, "enable-mtls", "", true, "Enable mTLS in your cluster")
InitCmd.Flags().BoolVarP(&enableHA, "enable-ha", "", false, "Enable high availability (HA) mode")
InitCmd.Flags().String("network", "", "The Docker network on which to deploy the Dapr runtime")
InitCmd.Flags().StringVarP(&fromDir, "from-dir", "", "", "Use Dapr artifacts from local directory for self-hosted installation")
InitCmd.Flags().StringVarP(&imageVariant, "image-variant", "", "", "The image variant to use for the Dapr runtime, for example: mariner")
InitCmd.Flags().StringVarP(&schedulerVolume, "scheduler-volume", "", "dapr_scheduler", "Self-hosted only. Specify a volume for the scheduler service data directory.")
InitCmd.Flags().StringVarP(&schedulerOverrideBroadcastHostPort, "scheduler-override-broadcast-host-port", "", "", "Self-hosted only. Specify the scheduler broadcast host and port, for example: 192.168.42.42:50006. If not specified, it uses localhost:50006 (6060 for Windows).")
InitCmd.Flags().BoolP("help", "h", false, "Print this help message")
InitCmd.Flags().StringArrayVar(&values, "set", []string{}, "set values on the command line (can specify multiple or separate values with commas: key1=val1,key2=val2)")
InitCmd.Flags().String("image-registry", "", "Custom/Private docker image repository url")
InitCmd.Flags().StringVarP(&containerRuntime, "container-runtime", "", "docker", "The container runtime to use (defaults to docker)")
InitCmd.Flags().String("image-registry", "", "Custom/private docker image repository URL")
InitCmd.Flags().StringVarP(&containerRuntime, "container-runtime", "", defaultContainerRuntime, "The container runtime to use. Supported values are docker (default) and podman")
InitCmd.Flags().StringVarP(&caRootCertificateFile, "ca-root-certificate", "", "", "The root certificate file")
InitCmd.Flags().StringVarP(&issuerPrivateKeyFile, "issuer-private-key", "", "", "The issuer certificate private key")
InitCmd.Flags().StringVarP(&issuerPublicCertificateFile, "issuer-public-certificate", "", "", "The issuer certificate")
InitCmd.MarkFlagsRequiredTogether("ca-root-certificate", "issuer-private-key", "issuer-public-certificate")
RootCmd.AddCommand(InitCmd)
}
// getConfigurationValue returns the value for a given configuration key.
// The value is retrieved from the following sources, in order:
// Default value
// Environment variable (respecting registered prefixes)
// Command line flag
// Value is returned as a string.
func getConfigurationValue(n string, cmd *cobra.Command) string {
viper.BindEnv(n)
viper.BindPFlag(n, cmd.Flags().Lookup(n))
return viper.GetString(n)
}

View File

@ -70,7 +70,7 @@ dapr invoke --unix-domain-socket --app-id target --method sample --verb GET
// TODO(@daixiang0): add Windows support.
if invokeSocket != "" {
if runtime.GOOS == "windows" {
if runtime.GOOS == string(windowsOsType) {
print.FailureStatusEvent(os.Stderr, "The unix-domain-socket option is not supported on Windows")
os.Exit(1)
} else {

View File

@ -67,7 +67,7 @@ dapr mtls export -o ./certs
}
dir, _ := filepath.Abs(exportPath)
print.SuccessStatusEvent(os.Stdout, fmt.Sprintf("Trust certs successfully exported to %s", dir))
print.SuccessStatusEvent(os.Stdout, "Trust certs successfully exported to "+dir)
},
PostRun: func(cmd *cobra.Command, args []string) {
kubernetes.CheckForCertExpiry()

View File

@ -69,7 +69,7 @@ dapr publish --publish-app-id myapp --pubsub target --topic sample --data '{"key
client := standalone.NewClient()
// TODO(@daixiang0): add Windows support.
if publishSocket != "" {
if runtime.GOOS == "windows" {
if runtime.GOOS == string(windowsOsType) {
print.FailureStatusEvent(os.Stderr, "The unix-domain-socket option is not supported on Windows")
os.Exit(1)
} else {

View File

@ -14,9 +14,11 @@ limitations under the License.
package cmd
import (
"errors"
"fmt"
"os"
"strings"
"sync"
"time"
"github.com/spf13/cobra"
@ -37,8 +39,9 @@ var (
func RenewCertificateCmd() *cobra.Command {
command := &cobra.Command{
Use: "renew-certificate",
Short: "Rotates Dapr root certificate of your kubernetes cluster",
Use: "renew-certificate",
Aliases: []string{"renew-cert", "rnc"},
Short: "Rotates the Dapr root certificate on your Kubernetes cluster",
Example: `
# Generates new root and issuer certificates for kubernetes cluster
@ -50,6 +53,13 @@ dapr mtls renew-certificate -k --private-key myprivatekey.key --valid-until <no
# Rotates certificate of your kubernetes cluster with provided ca.cert, issuer.crt and issuer.key file path
dapr mtls renew-certificate -k --ca-root-certificate <root.pem> --issuer-private-key <issuer.key> --issuer-public-certificate <issuer.pem> --restart
# Generates new root and issuer certificates for kubernetes cluster with provided image variant
dapr mtls renew-certificate -k --valid-until <no of days> --image-variant mariner --restart
# Use alias to renew certificate command
dapr mtls rnc -k --valid-until <no of days> --restart
dapr mtls renew-cert -k --valid-until <no of days> --restart
# See more at: https://docs.dapr.io/getting-started/
`,
@ -62,6 +72,10 @@ dapr mtls renew-certificate -k --ca-root-certificate <root.pem> --issuer-private
if kubernetesMode {
print.PendingStatusEvent(os.Stdout, "Starting certificate rotation")
err = utils.ValidateImageVariant(imageVariant)
if err != nil {
logErrorAndExit(err)
}
if rootcertFlag || issuerKeyFlag || issuerCertFlag {
flagArgsEmpty := checkReqFlagArgsEmpty(caRootCertificateFile, issuerPrivateKeyFile, issuerPublicCertificateFile)
if flagArgsEmpty {
@ -75,6 +89,7 @@ dapr mtls renew-certificate -k --ca-root-certificate <root.pem> --issuer-private
IssuerCertificateFilePath: issuerPublicCertificateFile,
IssuerPrivateKeyFilePath: issuerPrivateKeyFile,
Timeout: timeout,
ImageVariant: imageVariant,
})
if err != nil {
logErrorAndExit(err)
@ -88,8 +103,9 @@ dapr mtls renew-certificate -k --ca-root-certificate <root.pem> --issuer-private
print.InfoStatusEvent(os.Stdout, "Using password file to generate root certificate")
err = kubernetes.RenewCertificate(kubernetes.RenewCertificateParams{
RootPrivateKeyFilePath: privateKey,
ValidUntil: time.Hour * time.Duration(validUntil*24),
ValidUntil: time.Hour * time.Duration(validUntil*24), //nolint:gosec
Timeout: timeout,
ImageVariant: imageVariant,
})
if err != nil {
logErrorAndExit(err)
@ -97,8 +113,9 @@ dapr mtls renew-certificate -k --ca-root-certificate <root.pem> --issuer-private
} else {
print.InfoStatusEvent(os.Stdout, "generating fresh certificates")
err = kubernetes.RenewCertificate(kubernetes.RenewCertificateParams{
ValidUntil: time.Hour * time.Duration(validUntil*24),
Timeout: timeout,
ValidUntil: time.Hour * time.Duration(validUntil*24), //nolint:gosec
Timeout: timeout,
ImageVariant: imageVariant,
})
if err != nil {
logErrorAndExit(err)
@ -112,7 +129,7 @@ dapr mtls renew-certificate -k --ca-root-certificate <root.pem> --issuer-private
logErrorAndExit(err)
}
print.SuccessStatusEvent(os.Stdout,
fmt.Sprintf("Certificate rotation is successful! Your new certicate is valid through %s", expiry.Format(time.RFC1123)))
"Certificate rotation is successful! Your new certicate is valid through "+expiry.Format(time.RFC1123))
if restartDaprServices {
restartControlPlaneService()
@ -132,6 +149,7 @@ dapr mtls renew-certificate -k --ca-root-certificate <root.pem> --issuer-private
command.Flags().UintVarP(&validUntil, "valid-until", "", 365, "Max days before certificate expires")
command.Flags().BoolVarP(&restartDaprServices, "restart", "", false, "Restart Dapr control plane services")
command.Flags().UintVarP(&timeout, "timeout", "", 300, "The timeout for the certificate renewal")
command.Flags().StringVarP(&imageVariant, "image-variant", "", "", "The image variant to use for the Dapr runtime, for example: mariner")
command.MarkFlagRequired("kubernetes")
return command
}
@ -152,22 +170,43 @@ func logErrorAndExit(err error) {
}
func restartControlPlaneService() error {
controlPlaneServices := []string{"deploy/dapr-sentry", "deploy/dapr-operator", "statefulsets/dapr-placement-server"}
controlPlaneServices := []string{
"deploy/dapr-sentry",
"deploy/dapr-sidecar-injector",
"deploy/dapr-operator",
"statefulsets/dapr-placement-server",
}
namespace, err := kubernetes.GetDaprNamespace()
if err != nil {
print.FailureStatusEvent(os.Stdout, "Failed to fetch Dapr namespace")
}
for _, name := range controlPlaneServices {
print.InfoStatusEvent(os.Stdout, fmt.Sprintf("Restarting %s..", name))
_, err := utils.RunCmdAndWait("kubectl", "rollout", "restart", name, "-n", namespace)
if err != nil {
return fmt.Errorf("error in restarting deployment %s. Error is %w", name, err)
}
_, err = utils.RunCmdAndWait("kubectl", "rollout", "status", name, "-n", namespace)
if err != nil {
return fmt.Errorf("error in checking status for deployment %s. Error is %w", name, err)
}
errs := make([]error, len(controlPlaneServices))
var wg sync.WaitGroup
wg.Add(len(controlPlaneServices))
for i, name := range controlPlaneServices {
go func(i int, name string) {
defer wg.Done()
print.InfoStatusEvent(os.Stdout, fmt.Sprintf("Restarting %s..", name))
_, err := utils.RunCmdAndWait("kubectl", "rollout", "restart", "-n", namespace, name)
if err != nil {
errs[i] = fmt.Errorf("error in restarting deployment %s. Error is %w", name, err)
return
}
_, err = utils.RunCmdAndWait("kubectl", "rollout", "status", "-n", namespace, name)
if err != nil {
errs[i] = fmt.Errorf("error in checking status for deployment %s. Error is %w", name, err)
return
}
}(i, name)
}
wg.Wait()
if err := errors.Join(errs...); err != nil {
return err
}
print.SuccessStatusEvent(os.Stdout, "All control plane services have restarted successfully!")
return nil
}

View File

@ -16,46 +16,79 @@ package cmd
import (
"bufio"
"fmt"
"io"
"os"
"path/filepath"
"runtime"
"slices"
"strconv"
"strings"
"time"
"golang.org/x/mod/semver"
"github.com/spf13/cobra"
"github.com/spf13/pflag"
"github.com/spf13/viper"
daprRuntime "github.com/dapr/dapr/pkg/runtime"
"github.com/dapr/cli/pkg/kubernetes"
"github.com/dapr/cli/pkg/metadata"
"github.com/dapr/cli/pkg/print"
runExec "github.com/dapr/cli/pkg/runexec"
"github.com/dapr/cli/pkg/runfileconfig"
"github.com/dapr/cli/pkg/standalone"
daprsyscall "github.com/dapr/cli/pkg/syscall"
"github.com/dapr/cli/utils"
)
var (
appPort int
profilePort int
appID string
configFile string
port int
grpcPort int
internalGRPCPort int
maxConcurrency int
enableProfiling bool
logLevel string
protocol string
componentsPath string
appSSL bool
metricsPort int
maxRequestBodySize int
readBufferSize int
unixDomainSocket string
enableAPILogging bool
appPort int
profilePort int
appID string
configFile string
port int
grpcPort int
internalGRPCPort int
maxConcurrency int
enableProfiling bool
logLevel string
protocol string
componentsPath string
resourcesPaths []string
appSSL bool
metricsPort int
maxRequestBodySize string
readBufferSize string
unixDomainSocket string
enableAppHealth bool
appHealthPath string
appHealthInterval int
appHealthTimeout int
appHealthThreshold int
enableAPILogging bool
apiListenAddresses string
schedulerHostAddress string
runFilePath string
appChannelAddress string
enableRunK8s bool
)
const (
defaultRunTemplateFileName = "dapr.yaml"
runtimeWaitTimeoutInSeconds = 60
)
// Flags that are compatible with --run-file
var runFileCompatibleFlags = []string{
"kubernetes",
"help",
"version",
"runtime-path",
"log-as-json",
}
var RunCmd = &cobra.Command{
Use: "run",
Short: "Run Dapr and (optionally) your application side by side. Supported platforms: Self-hosted",
@ -77,19 +110,74 @@ dapr run --app-id myapp
# Run a gRPC application written in Go (listening on port 3000)
dapr run --app-id myapp --app-port 3000 --app-protocol grpc -- go run main.go
# Run a gRPC application written in Go (listening on port 3000) with a different app channel address
dapr run --app-id myapp --app-port 3000 --app-channel-address localhost --app-protocol grpc -- go run main.go
# Run sidecar only specifying dapr runtime installation directory
dapr run --app-id myapp --runtime-path /usr/local/dapr
# Run multiple apps by providing path of a run config file
dapr run --run-file dapr.yaml
# Run multiple apps by providing a directory path containing the run config file(dapr.yaml)
dapr run --run-file /path/to/directory
# Run multiple apps by providing config via stdin
cat dapr.template.yaml | envsubst | dapr run --run-file -
# Run multiple apps in Kubernetes by proficing path of a run config file
dapr run --run-file dapr.yaml -k
# Run multiple apps in Kubernetes by providing a directory path containing the run config file(dapr.yaml)
dapr run --run-file /path/to/directory -k
`,
Args: cobra.MinimumNArgs(0),
PreRun: func(cmd *cobra.Command, args []string) {
viper.BindPFlag("placement-host-address", cmd.Flags().Lookup("placement-host-address"))
},
Run: func(cmd *cobra.Command, args []string) {
if len(runFilePath) > 0 {
// Check for incompatible flags
incompatibleFlags := detectIncompatibleFlags(cmd)
if len(incompatibleFlags) > 0 {
// Print warning message about incompatible flags
warningMsg := "The following flags are ignored when using --run-file and should be configured in the run file instead: " + strings.Join(incompatibleFlags, ", ")
print.WarningStatusEvent(os.Stdout, warningMsg)
}
runConfigFilePath, err := getRunFilePath(runFilePath)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Failed to get run file path: %v", err)
os.Exit(1)
}
executeRunWithAppsConfigFile(runConfigFilePath, enableRunK8s)
return
}
if len(args) == 0 {
fmt.Println(print.WhiteBold("WARNING: no application command found."))
}
daprDirPath, err := standalone.GetDaprRuntimePath(daprRuntimePath)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Failed to get Dapr install directory: %v", err)
os.Exit(1)
}
// Fallback to default config file if not specified.
if configFile == "" {
configFile = standalone.GetDaprConfigPath(daprDirPath)
}
// Fallback to default components directory if not specified.
if componentsPath == "" {
componentsPath = standalone.GetDaprComponentsPath(daprDirPath)
}
if unixDomainSocket != "" {
// TODO(@daixiang0): add Windows support.
if runtime.GOOS == "windows" {
if runtime.GOOS == string(windowsOsType) {
print.FailureStatusEvent(os.Stderr, "The unix-domain-socket option is not supported on Windows")
os.Exit(1)
} else {
@ -100,35 +188,49 @@ dapr run --app-id myapp --app-port 3000 --app-protocol grpc -- go run main.go
}
}
output, err := standalone.Run(&standalone.RunConfig{
AppID: appID,
AppPort: appPort,
HTTPPort: port,
GRPCPort: grpcPort,
ConfigFile: configFile,
Arguments: args,
EnableProfiling: enableProfiling,
ProfilePort: profilePort,
LogLevel: logLevel,
MaxConcurrency: maxConcurrency,
Protocol: protocol,
PlacementHostAddr: viper.GetString("placement-host-address"),
ComponentsPath: componentsPath,
AppSSL: appSSL,
MetricsPort: metricsPort,
MaxRequestBodySize: maxRequestBodySize,
HTTPReadBufferSize: readBufferSize,
UnixDomainSocket: unixDomainSocket,
EnableAPILogging: enableAPILogging,
InternalGRPCPort: internalGRPCPort,
sharedRunConfig := &standalone.SharedRunConfig{
ConfigFile: configFile,
EnableProfiling: enableProfiling,
LogLevel: logLevel,
MaxConcurrency: maxConcurrency,
AppProtocol: protocol,
PlacementHostAddr: viper.GetString("placement-host-address"),
ComponentsPath: componentsPath,
ResourcesPaths: resourcesPaths,
AppSSL: appSSL,
MaxRequestBodySize: maxRequestBodySize,
HTTPReadBufferSize: readBufferSize,
EnableAppHealth: enableAppHealth,
AppHealthPath: appHealthPath,
AppHealthInterval: appHealthInterval,
AppHealthTimeout: appHealthTimeout,
AppHealthThreshold: appHealthThreshold,
EnableAPILogging: enableAPILogging,
APIListenAddresses: apiListenAddresses,
SchedulerHostAddress: schedulerHostAddress,
DaprdInstallPath: daprRuntimePath,
}
output, err := runExec.NewOutput(&standalone.RunConfig{
AppID: appID,
AppChannelAddress: appChannelAddress,
AppPort: appPort,
HTTPPort: port,
GRPCPort: grpcPort,
ProfilePort: profilePort,
Command: args,
MetricsPort: metricsPort,
UnixDomainSocket: unixDomainSocket,
InternalGRPCPort: internalGRPCPort,
SharedRunConfig: *sharedRunConfig,
})
if err != nil {
print.FailureStatusEvent(os.Stderr, err.Error())
os.Exit(1)
}
// TODO: In future release replace following logic with the refactored functions seen below.
sigCh := make(chan os.Signal, 1)
setupShutdownNotify(sigCh)
daprsyscall.SetupShutdownNotify(sigCh)
daprRunning := make(chan bool, 1)
appRunning := make(chan bool, 1)
@ -148,6 +250,15 @@ dapr run --app-id myapp --app-port 3000 --app-protocol grpc -- go run main.go
output.DaprHTTPPort,
output.DaprGRPCPort)
}
if (daprVer.RuntimeVersion != "edge") && (semver.Compare(fmt.Sprintf("v%v", daprVer.RuntimeVersion), "v1.14.0-rc.1") == -1) {
print.InfoStatusEvent(os.Stdout, "The scheduler is only compatible with dapr runtime 1.14 onwards.")
for i, arg := range output.DaprCMD.Args {
if strings.HasPrefix(arg, "--scheduler-host-address") {
output.DaprCMD.Args[i] = ""
}
}
}
print.InfoStatusEvent(os.Stdout, startInfo)
output.DaprCMD.Stdout = os.Stdout
@ -229,14 +340,14 @@ dapr run --app-id myapp --app-port 3000 --app-protocol grpc -- go run main.go
stdErrPipe, pipeErr := output.AppCMD.StderrPipe()
if pipeErr != nil {
print.FailureStatusEvent(os.Stderr, fmt.Sprintf("Error creating stderr for App: %s", err.Error()))
print.FailureStatusEvent(os.Stderr, "Error creating stderr for App: "+err.Error())
appRunning <- false
return
}
stdOutPipe, pipeErr := output.AppCMD.StdoutPipe()
if pipeErr != nil {
print.FailureStatusEvent(os.Stderr, fmt.Sprintf("Error creating stdout for App: %s", err.Error()))
print.FailureStatusEvent(os.Stderr, "Error creating stdout for App: "+err.Error())
appRunning <- false
return
}
@ -245,13 +356,13 @@ dapr run --app-id myapp --app-port 3000 --app-protocol grpc -- go run main.go
outScanner := bufio.NewScanner(stdOutPipe)
go func() {
for errScanner.Scan() {
fmt.Println(print.Blue(fmt.Sprintf("== APP == %s", errScanner.Text())))
fmt.Println(print.Blue("== APP == " + errScanner.Text()))
}
}()
go func() {
for outScanner.Scan() {
fmt.Println(print.Blue(fmt.Sprintf("== APP == %s", outScanner.Text())))
fmt.Println(print.Blue("== APP == " + outScanner.Text()))
}
}()
@ -290,15 +401,23 @@ dapr run --app-id myapp --app-port 3000 --app-protocol grpc -- go run main.go
}
// Metadata API is only available if app has started listening to port, so wait for app to start before calling metadata API.
err = metadata.Put(output.DaprHTTPPort, "cliPID", strconv.Itoa(os.Getpid()), appID, unixDomainSocket)
err = metadata.Put(output.DaprHTTPPort, "cliPID", strconv.Itoa(os.Getpid()), output.AppID, unixDomainSocket)
if err != nil {
print.WarningStatusEvent(os.Stdout, "Could not update sidecar metadata for cliPID: %s", err.Error())
}
if output.AppCMD != nil {
if output.AppCMD.Process != nil {
print.InfoStatusEvent(os.Stdout, fmt.Sprintf("Updating metadata for appPID: %d", output.AppCMD.Process.Pid))
err = metadata.Put(output.DaprHTTPPort, "appPID", strconv.Itoa(output.AppCMD.Process.Pid), output.AppID, unixDomainSocket)
if err != nil {
print.WarningStatusEvent(os.Stdout, "Could not update sidecar metadata for appPID: %s", err.Error())
}
}
appCommand := strings.Join(args, " ")
print.InfoStatusEvent(os.Stdout, fmt.Sprintf("Updating metadata for app command: %s", appCommand))
err = metadata.Put(output.DaprHTTPPort, "appCommand", appCommand, appID, unixDomainSocket)
print.InfoStatusEvent(os.Stdout, "Updating metadata for app command: "+appCommand)
err = metadata.Put(output.DaprHTTPPort, "appCommand", appCommand, output.AppID, unixDomainSocket)
if err != nil {
print.WarningStatusEvent(os.Stdout, "Could not update sidecar metadata for appCommand: %s", err.Error())
} else {
@ -354,7 +473,7 @@ dapr run --app-id myapp --app-port 3000 --app-protocol grpc -- go run main.go
func init() {
RunCmd.Flags().IntVarP(&appPort, "app-port", "p", -1, "The port your application is listening on")
RunCmd.Flags().StringVarP(&appID, "app-id", "a", "", "The id for your application, used for service discovery")
RunCmd.Flags().StringVarP(&configFile, "config", "c", standalone.DefaultConfigFilePath(), "Dapr configuration file")
RunCmd.Flags().StringVarP(&configFile, "config", "c", "", "Dapr configuration file")
RunCmd.Flags().IntVarP(&port, "dapr-http-port", "H", -1, "The HTTP port for Dapr to listen on")
RunCmd.Flags().IntVarP(&grpcPort, "dapr-grpc-port", "G", -1, "The gRPC port for Dapr to listen on")
RunCmd.Flags().IntVarP(&internalGRPCPort, "dapr-internal-grpc-port", "I", -1, "The gRPC port for the Dapr internal API to listen on")
@ -362,16 +481,625 @@ func init() {
RunCmd.Flags().IntVarP(&profilePort, "profile-port", "", -1, "The port for the profile server to listen on")
RunCmd.Flags().StringVarP(&logLevel, "log-level", "", "info", "The log verbosity. Valid values are: debug, info, warn, error, fatal, or panic")
RunCmd.Flags().IntVarP(&maxConcurrency, "app-max-concurrency", "", -1, "The concurrency level of the application, otherwise is unlimited")
RunCmd.Flags().StringVarP(&protocol, "app-protocol", "P", "http", "The protocol (gRPC or HTTP) Dapr uses to talk to the application")
RunCmd.Flags().StringVarP(&componentsPath, "components-path", "d", standalone.DefaultComponentsDirPath(), "The path for components directory")
RunCmd.Flags().StringVarP(&protocol, "app-protocol", "P", "http", "The protocol (grpc, grpcs, http, https, h2c) Dapr uses to talk to the application")
RunCmd.Flags().StringVarP(&componentsPath, "components-path", "d", "", "The path for components directory. Default is $HOME/.dapr/components or %USERPROFILE%\\.dapr\\components")
RunCmd.Flags().StringSliceVarP(&resourcesPaths, "resources-path", "", []string{}, "The path for resources directory")
// TODO: Remove below line once the flag is removed in the future releases.
// By marking this as deprecated, the flag will be hidden from the help menu, but will continue to work. It will show a warning message when used.
RunCmd.Flags().MarkDeprecated("components-path", "This flag is deprecated and will be removed in the future releases. Use \"resources-path\" flag instead")
RunCmd.Flags().String("placement-host-address", "localhost", "The address of the placement service. Format is either <hostname> for default port or <hostname>:<port> for custom port")
RunCmd.Flags().StringVarP(&schedulerHostAddress, "scheduler-host-address", "", "localhost", "The address of the scheduler service. Format is either <hostname> for default port or <hostname>:<port> for custom port")
// TODO: Remove below flag once the flag is removed in runtime in future release.
RunCmd.Flags().BoolVar(&appSSL, "app-ssl", false, "Enable https when Dapr invokes the application")
RunCmd.Flags().MarkDeprecated("app-ssl", "This flag is deprecated and will be removed in the future releases. Use \"app-protocol\" flag with https or grpcs values instead")
RunCmd.Flags().IntVarP(&metricsPort, "metrics-port", "M", -1, "The port of metrics on dapr")
RunCmd.Flags().BoolP("help", "h", false, "Print this help message")
RunCmd.Flags().IntVarP(&maxRequestBodySize, "dapr-http-max-request-size", "", -1, "Max size of request body in MB")
RunCmd.Flags().IntVarP(&readBufferSize, "dapr-http-read-buffer-size", "", -1, "HTTP header read buffer in KB")
RunCmd.Flags().StringVarP(&maxRequestBodySize, "max-body-size", "", strconv.Itoa(daprRuntime.DefaultMaxRequestBodySize>>20)+"Mi", "Max size of request body in MB")
RunCmd.Flags().StringVarP(&readBufferSize, "read-buffer-size", "", strconv.Itoa(daprRuntime.DefaultReadBufferSize>>10)+"Ki", "HTTP header read buffer in KB")
RunCmd.Flags().StringVarP(&unixDomainSocket, "unix-domain-socket", "u", "", "Path to a unix domain socket dir. If specified, Dapr API servers will use Unix Domain Sockets")
RunCmd.Flags().BoolVar(&enableAppHealth, "enable-app-health-check", false, "Enable health checks for the application using the protocol defined with app-protocol")
RunCmd.Flags().StringVar(&appHealthPath, "app-health-check-path", "", "Path used for health checks; HTTP only")
RunCmd.Flags().IntVar(&appHealthInterval, "app-health-probe-interval", 0, "Interval to probe for the health of the app in seconds")
RunCmd.Flags().IntVar(&appHealthTimeout, "app-health-probe-timeout", 0, "Timeout for app health probes in milliseconds")
RunCmd.Flags().IntVar(&appHealthThreshold, "app-health-threshold", 0, "Number of consecutive failures for the app to be considered unhealthy")
RunCmd.Flags().BoolVar(&enableAPILogging, "enable-api-logging", false, "Log API calls at INFO verbosity. Valid values are: true or false")
RunCmd.Flags().BoolVarP(&enableRunK8s, "kubernetes", "k", false, "Run the multi-app run template against Kubernetes environment.")
RunCmd.Flags().StringVar(&apiListenAddresses, "dapr-listen-addresses", "", "Comma separated list of IP addresses that sidecar will listen to")
RunCmd.Flags().StringVarP(&runFilePath, "run-file", "f", "", "Path to the run template file for the list of apps to run")
RunCmd.Flags().StringVarP(&appChannelAddress, "app-channel-address", "", utils.DefaultAppChannelAddress, "The network address the application listens on")
RootCmd.AddCommand(RunCmd)
}
func executeRun(runTemplateName, runFilePath string, apps []runfileconfig.App) (bool, error) {
var exitWithError bool
// setup shutdown notify channel.
sigCh := make(chan os.Signal, 1)
daprsyscall.SetupShutdownNotify(sigCh)
runStates := make([]*runExec.RunExec, 0, len(apps))
// Creates a separate process group ID for current process i.e. "dapr run -f".
// All the subprocess and their grandchildren inherit this PGID.
// This is done to provide a better grouping, which can be used to control all the proceses started by "dapr run -f".
daprsyscall.CreateProcessGroupID()
for _, app := range apps {
print.StatusEvent(os.Stdout, print.LogInfo, "Validating config and starting app %q", app.RunConfig.AppID)
// Set defaults if zero value provided in config yaml.
app.RunConfig.SetDefaultFromSchema()
app.RunConfig.SchedulerHostAddress = validateSchedulerHostAddress(daprVer.RuntimeVersion, app.RunConfig.SchedulerHostAddress)
// Validate validates the configs and modifies the ports to free ports, appId etc.
err := app.RunConfig.Validate()
if err != nil {
print.FailureStatusEvent(os.Stderr, "Error validating run config for app %q present in %s: %s", app.RunConfig.AppID, runFilePath, err.Error())
exitWithError = true
break
}
// Get Run Config for different apps.
runConfig := app.RunConfig
err = app.CreateDaprdLogFile()
if err != nil {
print.StatusEvent(os.Stderr, print.LogFailure, "Error getting daprd log file for app %q present in %s: %s", runConfig.AppID, runFilePath, err.Error())
exitWithError = true
break
}
// Combined multiwriter for logs.
var appDaprdWriter io.Writer
// appLogWriter is used when app command is present.
var appLogWriter io.Writer
// A custom writer used for trimming ASCII color codes from logs when writing to files.
var customAppLogWriter io.Writer
daprdLogWriterCloser := runfileconfig.GetLogWriter(app.DaprdLogWriteCloser, app.DaprdLogDestination)
if len(runConfig.Command) == 0 {
print.StatusEvent(os.Stdout, print.LogWarning, "No application command found for app %q present in %s", runConfig.AppID, runFilePath)
appDaprdWriter = runExec.GetAppDaprdWriter(app, true)
appLogWriter = app.DaprdLogWriteCloser
} else {
err = app.CreateAppLogFile()
if err != nil {
print.StatusEvent(os.Stderr, print.LogFailure, "Error getting app log file for app %q present in %s: %s", runConfig.AppID, runFilePath, err.Error())
exitWithError = true
break
}
appDaprdWriter = runExec.GetAppDaprdWriter(app, false)
appLogWriter = runfileconfig.GetLogWriter(app.AppLogWriteCloser, app.AppLogDestination)
}
customAppLogWriter = print.CustomLogWriter{W: appLogWriter}
runState, err := startDaprdAndAppProcesses(&runConfig, app.AppDirPath, sigCh,
daprdLogWriterCloser, daprdLogWriterCloser, customAppLogWriter, customAppLogWriter)
if err != nil {
print.StatusEvent(appDaprdWriter, print.LogFailure, "Error starting Dapr and app (%q): %s", app.AppID, err.Error())
exitWithError = true
break
}
// Store runState in an array.
runStates = append(runStates, runState)
// Metadata API is only available if app has started listening to port, so wait for app to start before calling metadata API.
putCLIProcessIDInMeta(runState, os.Getpid())
// Update extended metadata with run file path.
putRunFilePathInMeta(runState, runFilePath)
// Update extended metadata with run file path.
putRunTemplateNameInMeta(runState, runTemplateName)
// Update extended metadata with app log file path.
if app.AppLogDestination != standalone.Console {
putAppLogFilePathInMeta(runState, app.AppLogFileName)
}
// Update extended metadata with daprd log file path.
if app.DaprdLogDestination != standalone.Console {
putDaprLogFilePathInMeta(runState, app.DaprdLogFileName)
}
if runState.AppCMD.Command != nil {
putAppCommandInMeta(runConfig, runState)
if runState.AppCMD.Command.Process != nil {
putAppProcessIDInMeta(runState)
// Attach a windows job object to the app process.
utils.AttachJobObjectToProcess(strconv.Itoa(os.Getpid()), runState.AppCMD.Command.Process)
}
}
print.StatusEvent(runState.DaprCMD.OutputWriter, print.LogSuccess, "You're up and running! Dapr logs will appear here.\n")
logInformationalStatusToStdout(app)
}
// If all apps have been started and there are no errors in starting the apps wait for signal from sigCh.
if !exitWithError {
// After all apps started wait for sigCh.
<-sigCh
// To add a new line in Stdout.
fmt.Println()
print.InfoStatusEvent(os.Stdout, "Received signal to stop Dapr and app processes. Shutting down Dapr and app processes.")
}
// Stop daprd and app processes for each runState.
closeError := gracefullyShutdownAppsAndCloseResources(runStates, apps)
for _, app := range apps {
runConfig := app.RunConfig
if runConfig.UnixDomainSocket != "" {
for _, s := range []string{"http", "grpc"} {
os.Remove(utils.GetSocket(runConfig.UnixDomainSocket, runConfig.AppID, s))
}
}
}
return exitWithError, closeError
}
func logInformationalStatusToStdout(app runfileconfig.App) {
print.InfoStatusEvent(os.Stdout, "Started Dapr with app id %q. HTTP Port: %d. gRPC Port: %d",
app.AppID, app.RunConfig.HTTPPort, app.RunConfig.GRPCPort)
print.InfoStatusEvent(os.Stdout, "Writing log files to directory : %s", app.GetLogsDir())
}
func gracefullyShutdownAppsAndCloseResources(runState []*runExec.RunExec, apps []runfileconfig.App) error {
for _, s := range runState {
stopDaprdAndAppProcesses(s)
}
var err error
// close log file resources.
for _, app := range apps {
hasErr := app.CloseAppLogFile()
if err == nil && hasErr != nil {
err = hasErr
}
hasErr = app.CloseDaprdLogFile()
if err == nil && hasErr != nil {
err = hasErr
}
}
return err
}
func executeRunWithAppsConfigFile(runFilePath string, k8sEnabled bool) {
config, apps, err := getRunConfigFromRunFile(runFilePath)
if err != nil {
print.StatusEvent(os.Stdout, print.LogFailure, "Error getting apps from config file: %s", err)
os.Exit(1)
}
if len(apps) == 0 {
print.StatusEvent(os.Stdout, print.LogFailure, "No apps to run")
os.Exit(1)
}
var exitWithError bool
var closeErr error
if !k8sEnabled {
exitWithError, closeErr = executeRun(config.Name, runFilePath, apps)
} else {
exitWithError, closeErr = kubernetes.Run(runFilePath, config)
}
if exitWithError {
if closeErr != nil {
print.StatusEvent(os.Stdout, print.LogFailure, "Error closing resources: %s", closeErr)
}
os.Exit(1)
}
}
// populate the scheduler host address based on the dapr version.
func validateSchedulerHostAddress(version, address string) string {
// If no SchedulerHostAddress is supplied, set it to default value.
if semver.Compare(fmt.Sprintf("v%v", version), "v1.15.0-rc.0") == 1 {
if address == "" {
return "localhost"
}
}
return address
}
func getRunConfigFromRunFile(runFilePath string) (runfileconfig.RunFileConfig, []runfileconfig.App, error) {
config := runfileconfig.RunFileConfig{}
apps, err := config.GetApps(runFilePath)
return config, apps, err
}
// startDaprdAndAppProcesses is a function to start the App process and the associated Daprd process.
// This should be called as a blocking function call.
func startDaprdAndAppProcesses(runConfig *standalone.RunConfig, commandDir string, sigCh chan os.Signal,
daprdOutputWriter io.Writer, daprdErrorWriter io.Writer,
appOutputWriter io.Writer, appErrorWriter io.Writer,
) (*runExec.RunExec, error) {
daprRunning := make(chan bool, 1)
appRunning := make(chan bool, 1)
daprCMD, err := runExec.GetDaprCmdProcess(runConfig)
if err != nil {
print.StatusEvent(daprdErrorWriter, print.LogFailure, "Error getting daprd command with args : %s", err.Error())
return nil, err
}
if strings.TrimSpace(commandDir) != "" {
daprCMD.Command.Dir = commandDir
}
daprCMD.WithOutputWriter(daprdOutputWriter)
daprCMD.WithErrorWriter(daprdErrorWriter)
daprCMD.SetStdout()
daprCMD.SetStderr()
appCmd, err := runExec.GetAppCmdProcess(runConfig)
if err != nil {
print.StatusEvent(appErrorWriter, print.LogFailure, "Error getting app command with args : %s", err.Error())
return nil, err
}
if appCmd.Command != nil {
// If an app is being run, set the command directory for that app.
// appCmd does not need to call SetStdout and SetStderr since output is being read processed and then written
// to the output and error writers for an app.
appCmd.WithOutputWriter(appOutputWriter)
appCmd.WithErrorWriter(appErrorWriter)
if strings.TrimSpace(commandDir) != "" {
appCmd.Command.Dir = commandDir
}
}
runState := runExec.New(runConfig, daprCMD, appCmd)
startErrChan := make(chan error, 1)
// Start daprd process.
go startDaprdProcess(runConfig, runState, daprRunning, sigCh, startErrChan)
// Wait for daprRunning channel output.
if daprStarted := <-daprRunning; !daprStarted {
startErr := <-startErrChan
print.StatusEvent(daprdErrorWriter, print.LogFailure, "Error starting daprd process: %s", startErr.Error())
return nil, startErr
}
// No application command is present.
if appCmd.Command == nil {
print.StatusEvent(appOutputWriter, print.LogWarning, "No application command present")
return runState, nil
}
// Start App process.
go startAppProcess(runConfig, runState, appRunning, sigCh, startErrChan)
// Wait for appRunnning channel output.
if appStarted := <-appRunning; !appStarted {
startErr := <-startErrChan
print.StatusEvent(appErrorWriter, print.LogFailure, "Error starting app process: %s", startErr.Error())
// Start App failed so try to stop daprd process.
err = killDaprdProcess(runState)
if err != nil {
print.StatusEvent(daprdErrorWriter, print.LogFailure, "Error stopping daprd process: %s", err.Error())
print.StatusEvent(appErrorWriter, print.LogFailure, "Error stopping daprd process: %s", err.Error())
}
// Return the error from starting the app process.
return nil, startErr
}
return runState, nil
}
// stopDaprdAndAppProcesses is a function to stop the App process and the associated Daprd process
// This should be called as a blocking function call.
func stopDaprdAndAppProcesses(runState *runExec.RunExec) bool {
var err error
print.StatusEvent(runState.DaprCMD.OutputWriter, print.LogInfo, "\ntermination signal received: shutting down")
// Only if app command is present and
// if two different output writers are present run the following print statement.
if runState.AppCMD.Command != nil && runState.AppCMD.OutputWriter != runState.DaprCMD.OutputWriter {
print.StatusEvent(runState.AppCMD.OutputWriter, print.LogInfo, "\ntermination signal received: shutting down")
}
exitWithError := false
daprErr := runState.DaprCMD.CommandErr
if daprErr != nil {
exitWithError = true
print.StatusEvent(runState.DaprCMD.ErrorWriter, print.LogFailure, "Error exiting Dapr: %s", daprErr)
} else if runState.DaprCMD.Command.ProcessState == nil || !runState.DaprCMD.Command.ProcessState.Exited() {
err = killDaprdProcess(runState)
if err != nil {
exitWithError = true
}
}
appErr := runState.AppCMD.CommandErr
if appErr != nil {
exitWithError = true
print.StatusEvent(runState.AppCMD.ErrorWriter, print.LogFailure, "Error exiting App: %s", appErr)
} else if runState.AppCMD.Command != nil && (runState.AppCMD.Command.ProcessState == nil || !runState.AppCMD.Command.ProcessState.Exited()) {
err = killAppProcess(runState)
if err != nil {
exitWithError = true
}
}
return exitWithError
}
// startAppsProcess, starts the App process and calls wait in a goroutine
// This function should be called as a goroutine.
func startAppProcess(runConfig *standalone.RunConfig, runE *runExec.RunExec,
appRunning chan bool, sigCh chan os.Signal, errorChan chan error,
) {
if runE.AppCMD.Command == nil {
appRunning <- true
return
}
stdErrPipe, pipeErr := runE.AppCMD.Command.StderrPipe()
if pipeErr != nil {
print.StatusEvent(runE.AppCMD.ErrorWriter, print.LogFailure, "Error creating stderr for App %q : %s", runE.AppID, pipeErr.Error())
errorChan <- pipeErr
appRunning <- false
return
}
stdOutPipe, pipeErr := runE.AppCMD.Command.StdoutPipe()
if pipeErr != nil {
print.StatusEvent(runE.AppCMD.ErrorWriter, print.LogFailure, "Error creating stdout for App %q : %s", runE.AppID, pipeErr.Error())
errorChan <- pipeErr
appRunning <- false
return
}
errScanner := bufio.NewScanner(stdErrPipe)
outScanner := bufio.NewScanner(stdOutPipe)
go func() {
for errScanner.Scan() {
fmt.Fprintln(runE.AppCMD.ErrorWriter, print.Blue(fmt.Sprintf("== APP - %s == %s", runE.AppID,
errScanner.Text())))
}
}()
go func() {
for outScanner.Scan() {
fmt.Fprintln(runE.AppCMD.OutputWriter, print.Blue(fmt.Sprintf("== APP - %s == %s", runE.AppID, outScanner.Text())))
}
}()
err := runE.AppCMD.Command.Start()
if err != nil {
print.StatusEvent(runE.AppCMD.ErrorWriter, print.LogFailure, err.Error())
errorChan <- err
appRunning <- false
return
}
go func() {
appErr := runE.AppCMD.Command.Wait()
if appErr != nil {
runE.AppCMD.CommandErr = appErr
print.StatusEvent(runE.AppCMD.ErrorWriter, print.LogFailure, "The App process exited with error code: %s", appErr.Error())
} else {
print.StatusEvent(runE.AppCMD.OutputWriter, print.LogSuccess, "Exited App successfully")
}
}()
appRunning <- true
}
// startDaprdProcess, starts the Daprd process and calls wait in a goroutine
// This function should be called as a goroutine.
func startDaprdProcess(runConfig *standalone.RunConfig, runE *runExec.RunExec,
daprRunning chan bool, sigCh chan os.Signal, errorChan chan error,
) {
var startInfo string
if runConfig.UnixDomainSocket != "" {
startInfo = fmt.Sprintf(
"Starting Dapr with id %s. HTTP Socket: %v. gRPC Socket: %v.",
runE.AppID,
utils.GetSocket(unixDomainSocket, runE.AppID, "http"),
utils.GetSocket(unixDomainSocket, runE.AppID, "grpc"))
} else {
startInfo = fmt.Sprintf(
"Starting Dapr with id %s. HTTP Port: %v. gRPC Port: %v",
runE.AppID,
runE.DaprHTTPPort,
runE.DaprGRPCPort)
}
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogInfo, startInfo)
err := runE.DaprCMD.Command.Start()
if err != nil {
errorChan <- err
daprRunning <- false
return
}
go func() {
daprdErr := runE.DaprCMD.Command.Wait()
if daprdErr != nil {
runE.DaprCMD.CommandErr = daprdErr
print.StatusEvent(runE.DaprCMD.ErrorWriter, print.LogFailure, "The daprd process exited with error code: %s", daprdErr.Error())
} else {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogSuccess, "Exited Dapr successfully")
}
}()
if runConfig.AppPort <= 0 {
// If app does not listen to port, we can check for Dapr's sidecar health before starting the app.
// Otherwise, it creates a deadlock.
sidecarUp := true
if runConfig.UnixDomainSocket != "" {
httpSocket := utils.GetSocket(runConfig.UnixDomainSocket, runE.AppID, "http")
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogInfo, "Checking if Dapr sidecar is listening on HTTP socket %v", httpSocket)
err = utils.IsDaprListeningOnSocket(httpSocket, time.Duration(runtimeWaitTimeoutInSeconds)*time.Second)
if err != nil {
sidecarUp = false
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Dapr sidecar is not listening on HTTP socket: %s", err.Error())
}
grpcSocket := utils.GetSocket(runConfig.UnixDomainSocket, runE.AppID, "grpc")
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogInfo, "Checking if Dapr sidecar is listening on GRPC socket %v", grpcSocket)
err = utils.IsDaprListeningOnSocket(grpcSocket, time.Duration(runtimeWaitTimeoutInSeconds)*time.Second)
if err != nil {
sidecarUp = false
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Dapr sidecar is not listening on GRPC socket: %s", err.Error())
}
} else {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogInfo, "Checking if Dapr sidecar is listening on HTTP port %v", runE.DaprHTTPPort)
err = utils.IsDaprListeningOnPort(runE.DaprHTTPPort, time.Duration(runtimeWaitTimeoutInSeconds)*time.Second)
if err != nil {
sidecarUp = false
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Dapr sidecar is not listening on HTTP port: %s", err.Error())
}
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogInfo, "Checking if Dapr sidecar is listening on GRPC port %v", runE.DaprGRPCPort)
err = utils.IsDaprListeningOnPort(runE.DaprGRPCPort, time.Duration(runtimeWaitTimeoutInSeconds)*time.Second)
if err != nil {
sidecarUp = false
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Dapr sidecar is not listening on GRPC port: %s", err.Error())
}
}
if sidecarUp {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogInfo, "Dapr sidecar is up and running.")
} else {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Dapr sidecar might not be responding.")
}
}
daprRunning <- true
}
// killDaprdProcess is used to kill the Daprd process and return error on failure.
func killDaprdProcess(runE *runExec.RunExec) error {
err := runE.DaprCMD.Command.Process.Kill()
if err != nil {
print.StatusEvent(runE.DaprCMD.ErrorWriter, print.LogFailure, "Error exiting Dapr: %s", err)
return err
}
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogSuccess, "Exited Dapr successfully")
return nil
}
// killAppProcess is used to kill the App process and return error on failure.
func killAppProcess(runE *runExec.RunExec) error {
if runE.AppCMD.Command == nil {
return nil
}
err := runE.AppCMD.Command.Process.Kill()
if err != nil {
print.StatusEvent(runE.DaprCMD.ErrorWriter, print.LogFailure, "Error exiting App: %s", err)
return err
}
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogSuccess, "Exited App successfully")
return nil
}
// putCLIProcessIDInMeta puts the CLI process ID in metadata so that it can be used by the CLI to stop the CLI process.
func putCLIProcessIDInMeta(runE *runExec.RunExec, pid int) {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogInfo, "Updating metadata for cliPID: %d", pid)
err := metadata.Put(runE.DaprHTTPPort, "cliPID", strconv.Itoa(pid), runE.AppID, unixDomainSocket)
if err != nil {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Could not update sidecar metadata for cliPID: %s", err.Error())
}
}
func putAppProcessIDInMeta(runE *runExec.RunExec) {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogInfo, "Updating metadata for appPID: %d", runE.AppCMD.Command.Process.Pid)
err := metadata.Put(runE.DaprHTTPPort, "appPID", strconv.Itoa(runE.AppCMD.Command.Process.Pid), runE.AppID, unixDomainSocket)
if err != nil {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Could not update sidecar metadata for appPID: %s", err.Error())
}
}
// putAppCommandInMeta puts the app command in metadata so that it can be used by the CLI to stop the app.
func putAppCommandInMeta(runConfig standalone.RunConfig, runE *runExec.RunExec) {
appCommand := strings.Join(runConfig.Command, " ")
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogInfo, "Updating metadata for app command: %s", appCommand)
err := metadata.Put(runE.DaprHTTPPort, "appCommand", appCommand, runE.AppID, runConfig.UnixDomainSocket)
if err != nil {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Could not update sidecar metadata for appCommand: %s", err.Error())
return
}
}
// putRunFilePathInMeta puts the absolute path of run file in metadata so that it can be used by the CLI to stop all apps started by this run file.
func putRunFilePathInMeta(runE *runExec.RunExec, runFilePath string) {
runFilePath, err := filepath.Abs(runFilePath)
if err != nil {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Could not get absolute path for run file: %s", err.Error())
return
}
err = metadata.Put(runE.DaprHTTPPort, "runTemplatePath", runFilePath, runE.AppID, unixDomainSocket)
if err != nil {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Could not update sidecar metadata for run file path: %s", err.Error())
}
}
// putRunTemplateNameInMeta puts the name of the run file in metadata so that it can be used by the CLI to stop all apps started by this run file.
func putRunTemplateNameInMeta(runE *runExec.RunExec, runTemplateName string) {
err := metadata.Put(runE.DaprHTTPPort, "runTemplateName", runTemplateName, runE.AppID, unixDomainSocket)
if err != nil {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Could not update sidecar metadata for run template name: %s", err.Error())
}
}
// putAppLogFilePathInMeta puts the absolute path of app log file in metadata so that it can be used by the CLI to stop the app.
func putAppLogFilePathInMeta(runE *runExec.RunExec, appLogFilePath string) {
err := metadata.Put(runE.DaprHTTPPort, "appLogPath", appLogFilePath, runE.AppID, unixDomainSocket)
if err != nil {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Could not update sidecar metadata for app log file path: %s", err.Error())
}
}
// putDaprLogFilePathInMeta puts the absolute path of Dapr log file in metadata so that it can be used by the CLI to stop the app.
func putDaprLogFilePathInMeta(runE *runExec.RunExec, daprLogFilePath string) {
err := metadata.Put(runE.DaprHTTPPort, "daprdLogPath", daprLogFilePath, runE.AppID, unixDomainSocket)
if err != nil {
print.StatusEvent(runE.DaprCMD.OutputWriter, print.LogWarning, "Could not update sidecar metadata for dapr log file path: %s", err.Error())
}
}
// getRunFilePath returns the path to the run file.
// If the provided path is a path to a YAML file then return the same.
// Else it returns the path of "dapr.yaml" in the provided directory.
func getRunFilePath(path string) (string, error) {
if path == "-" {
return path, nil // will be read from stdin later.
}
fileInfo, err := os.Stat(path)
if err != nil {
return "", fmt.Errorf("error getting file info for %s: %w", path, err)
}
if fileInfo.IsDir() {
filePath, err := utils.FindFileInDir(path, defaultRunTemplateFileName)
if err != nil {
return "", err
}
return filePath, nil
}
hasYAMLExtension := strings.HasSuffix(path, ".yaml") || strings.HasSuffix(path, ".yml")
if !hasYAMLExtension {
return "", fmt.Errorf("file %q is not a YAML file", path)
}
return path, nil
}
// getConflictingFlags checks if any flags are set other than the ones passed in the excludedFlags slice.
// Used for logic or notifications when any of the flags are conflicting and should not be used together.
func getConflictingFlags(cmd *cobra.Command, excludedFlags ...string) []string {
var conflictingFlags []string
cmd.Flags().Visit(func(f *pflag.Flag) {
if !slices.Contains(excludedFlags, f.Name) {
conflictingFlags = append(conflictingFlags, f.Name)
}
})
return conflictingFlags
}
// detectIncompatibleFlags checks if any incompatible flags are used with --run-file
// and returns a slice of the flag names that were used
func detectIncompatibleFlags(cmd *cobra.Command) []string {
if runFilePath == "" {
return nil // No run file specified, so no incompatibilities
}
// Get all flags that are not in the compatible list
return getConflictingFlags(cmd, append(runFileCompatibleFlags, "run-file")...)
}

78
cmd/run_test.go Normal file
View File

@ -0,0 +1,78 @@
package cmd
import (
"testing"
"github.com/spf13/cobra"
"github.com/stretchr/testify/assert"
)
func TestValidateSchedulerHostAddress(t *testing.T) {
t.Run("test scheduler host address - v1.14.0-rc.0", func(t *testing.T) {
address := validateSchedulerHostAddress("1.14.0-rc.0", "")
assert.Equal(t, "", address)
})
t.Run("test scheduler host address - v1.15.0-rc.0", func(t *testing.T) {
address := validateSchedulerHostAddress("1.15.0", "")
assert.Equal(t, "localhost:50006", address)
})
}
func TestDetectIncompatibleFlags(t *testing.T) {
// Setup a temporary run file path to trigger the incompatible flag check
originalRunFilePath := runFilePath
runFilePath = "some/path"
defer func() {
// Restore the original runFilePath
runFilePath = originalRunFilePath
}()
t.Run("detect incompatible flags", func(t *testing.T) {
// Create a test command with flags
cmd := &cobra.Command{Use: "test"}
cmd.Flags().String("app-id", "", "")
cmd.Flags().String("dapr-http-port", "", "")
cmd.Flags().String("kubernetes", "", "") // Compatible flag
cmd.Flags().String("runtime-path", "", "") // Compatible flag
cmd.Flags().String("log-as-json", "", "") // Compatible flag
// Mark flags as changed
cmd.Flags().Set("app-id", "myapp")
cmd.Flags().Set("dapr-http-port", "3500")
cmd.Flags().Set("kubernetes", "true")
cmd.Flags().Set("runtime-path", "/path/to/runtime")
cmd.Flags().Set("log-as-json", "true")
// Test detection
incompatibleFlags := detectIncompatibleFlags(cmd)
assert.Len(t, incompatibleFlags, 2)
assert.Contains(t, incompatibleFlags, "app-id")
assert.Contains(t, incompatibleFlags, "dapr-http-port")
assert.NotContains(t, incompatibleFlags, "kubernetes")
assert.NotContains(t, incompatibleFlags, "runtime-path")
assert.NotContains(t, incompatibleFlags, "log-as-json")
})
t.Run("no incompatible flags when run file not specified", func(t *testing.T) {
// Create a test command with flags
cmd := &cobra.Command{Use: "test"}
cmd.Flags().String("app-id", "", "")
cmd.Flags().String("dapr-http-port", "", "")
// Mark flags as changed
cmd.Flags().Set("app-id", "myapp")
cmd.Flags().Set("dapr-http-port", "3500")
// Temporarily clear runFilePath
originalRunFilePath := runFilePath
runFilePath = ""
defer func() {
runFilePath = originalRunFilePath
}()
// Test detection
incompatibleFlags := detectIncompatibleFlags(cmd)
assert.Nil(t, incompatibleFlags)
})
}

View File

@ -1,42 +0,0 @@
/*
Copyright 2021 The Dapr Authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package cmd
import (
"fmt"
"os"
"os/signal"
"syscall"
"golang.org/x/sys/windows"
"github.com/dapr/cli/pkg/print"
)
func setupShutdownNotify(sigCh chan os.Signal) {
signal.Notify(sigCh, syscall.SIGTERM, syscall.SIGINT)
// Unlike Linux/Mac, you can't just send a SIGTERM from another process.
// In order for 'dapr stop' to be able to signal gracefully we must use a named event in Windows.
go func() {
eventName, _ := syscall.UTF16FromString(fmt.Sprintf("dapr_cli_%v", os.Getpid()))
eventHandle, _ := windows.CreateEvent(nil, 0, 0, &eventName[0])
_, err := windows.WaitForSingleObject(eventHandle, windows.INFINITE)
if err != nil {
print.WarningStatusEvent(os.Stdout, "Unable to wait for shutdown event. 'dapr stop' will not work. Error: %s", err.Error())
return
}
sigCh <- os.Interrupt
}()
}

View File

@ -14,15 +14,21 @@ limitations under the License.
package cmd
import (
"fmt"
"os"
"path/filepath"
"github.com/spf13/cobra"
"github.com/dapr/cli/pkg/kubernetes"
"github.com/dapr/cli/pkg/print"
"github.com/dapr/cli/pkg/standalone"
)
var stopAppID string
var (
stopAppID string
stopK8s bool
)
var StopCmd = &cobra.Command{
Use: "stop",
@ -30,13 +36,56 @@ var StopCmd = &cobra.Command{
Example: `
# Stop Dapr application
dapr stop --app-id <ID>
# Stop multiple apps by providing a run config file
dapr stop --run-file dapr.yaml
# Stop multiple apps by providing a directory path containing the run config file(dapr.yaml)
dapr stop --run-file /path/to/directory
# Stop and delete Kubernetes deployment of multiple apps by providing a run config file
dapr stop --run-file dapr.yaml -k
# Stop and delete Kubernetes deployment of multiple apps by providing a directory path containing the run config file(dapr.yaml)
dapr stop --run-file /path/to/directory -k
`,
Run: func(cmd *cobra.Command, args []string) {
var err error
if len(runFilePath) > 0 {
runFilePath, err = getRunFilePath(runFilePath)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Failed to get run file path: %v", err)
os.Exit(1)
}
if !stopK8s {
err = executeStopWithRunFile(runFilePath)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Failed to stop Dapr and app processes: %s", err)
} else {
print.SuccessStatusEvent(os.Stdout, "Dapr and app processes stopped successfully")
}
return
}
config, _, cErr := getRunConfigFromRunFile(runFilePath)
if cErr != nil {
print.FailureStatusEvent(os.Stderr, "Failed to parse run template file %q: %s", runFilePath, cErr.Error())
}
err = kubernetes.Stop(runFilePath, config)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Error stopping deployments from multi-app run template: %v", err)
}
}
if stopAppID != "" {
args = append(args, stopAppID)
}
apps, err := standalone.List()
if err != nil {
print.FailureStatusEvent(os.Stderr, "failed to get list of apps started by dapr : %s", err)
os.Exit(1)
}
cliPIDToNoOfApps := standalone.GetCLIPIDCountMap(apps)
for _, appID := range args {
err := standalone.Stop(appID)
err = standalone.Stop(appID, cliPIDToNoOfApps, apps)
if err != nil {
print.FailureStatusEvent(os.Stderr, "failed to stop app id %s: %s", appID, err)
} else {
@ -48,6 +97,16 @@ dapr stop --app-id <ID>
func init() {
StopCmd.Flags().StringVarP(&stopAppID, "app-id", "a", "", "The application id to be stopped")
StopCmd.Flags().StringVarP(&runFilePath, "run-file", "f", "", "Path to the run template file for the list of apps to stop")
StopCmd.Flags().BoolVarP(&stopK8s, "kubernetes", "k", false, "Stop deployments in Kubernetes based on multi-app run file")
StopCmd.Flags().BoolP("help", "h", false, "Print this help message")
RootCmd.AddCommand(StopCmd)
}
func executeStopWithRunFile(runFilePath string) error {
absFilePath, err := filepath.Abs(runFilePath)
if err != nil {
return fmt.Errorf("failed to get absolute file path for %s: %w", runFilePath, err)
}
return standalone.StopAppsWithRunFile(absFilePath)
}

View File

@ -16,6 +16,7 @@ package cmd
import (
"fmt"
"os"
"strings"
"github.com/spf13/cobra"
"github.com/spf13/viper"
@ -23,11 +24,13 @@ import (
"github.com/dapr/cli/pkg/kubernetes"
"github.com/dapr/cli/pkg/print"
"github.com/dapr/cli/pkg/standalone"
"github.com/dapr/cli/utils"
)
var (
uninstallNamespace string
uninstallKubernetes bool
uninstallDev bool
uninstallAll bool
uninstallContainerRuntime string
)
@ -40,11 +43,24 @@ var UninstallCmd = &cobra.Command{
# Uninstall from self-hosted mode
dapr uninstall
# Uninstall from self-hosted mode and remove .dapr directory, Redis, Placement and Zipkin containers
# Uninstall from self-hosted mode and remove .dapr directory, Redis, Placement, Scheduler, and Zipkin containers
dapr uninstall --all
# Uninstall from Kubernetes
dapr uninstall -k
# Uninstall from Kubernetes and remove CRDs
dapr uninstall -k --all
# Uninstall from Kubernetes remove dev deployments of Redis, Zipkin
dapr uninstall -k --dev
# Uninstall from Kubernetes remove dev deployments of Redis, Zipkin and CRDs
dapr uninstall -k --dev --all
# Uninstall Dapr from non-default install directory
# This will remove the .dapr directory present in the path <path-to-install-directory>
dapr uninstall --runtime-path <path-to-install-directory>
`,
PreRun: func(cmd *cobra.Command, args []string) {
viper.BindPFlag("network", cmd.Flags().Lookup("network"))
@ -54,12 +70,21 @@ dapr uninstall -k
var err error
if uninstallKubernetes {
if len(strings.TrimSpace(daprRuntimePath)) != 0 {
print.FailureStatusEvent(os.Stderr, "--runtime-path is only valid for self-hosted mode")
os.Exit(1)
}
print.InfoStatusEvent(os.Stdout, "Removing Dapr from your cluster...")
err = kubernetes.Uninstall(uninstallNamespace, uninstallAll, timeout)
err = kubernetes.Uninstall(uninstallNamespace, uninstallAll, uninstallDev, timeout)
} else {
if !utils.IsValidContainerRuntime(uninstallContainerRuntime) {
print.FailureStatusEvent(os.Stdout, "Invalid container runtime. Supported values are docker and podman.")
os.Exit(1)
}
print.InfoStatusEvent(os.Stdout, "Removing Dapr from your machine...")
dockerNetwork := viper.GetString("network")
err = standalone.Uninstall(uninstallAll, dockerNetwork, uninstallContainerRuntime)
err = standalone.Uninstall(uninstallAll, dockerNetwork, uninstallContainerRuntime, daprRuntimePath)
}
if err != nil {
@ -72,11 +97,12 @@ dapr uninstall -k
func init() {
UninstallCmd.Flags().BoolVarP(&uninstallKubernetes, "kubernetes", "k", false, "Uninstall Dapr from a Kubernetes cluster")
UninstallCmd.Flags().BoolVarP(&uninstallDev, "dev", "", false, "Uninstall Dapr Redis and Zipking installations from Kubernetes cluster")
UninstallCmd.Flags().UintVarP(&timeout, "timeout", "", 300, "The timeout for the Kubernetes uninstall")
UninstallCmd.Flags().BoolVar(&uninstallAll, "all", false, "Remove .dapr directory, Redis, Placement and Zipkin containers on local machine, and CRDs on a Kubernetes cluster")
UninstallCmd.Flags().BoolVar(&uninstallAll, "all", false, "Remove .dapr directory, Redis, Placement, Scheduler (and default volume in self-hosted mode), and Zipkin containers on local machine, and CRDs on a Kubernetes cluster")
UninstallCmd.Flags().String("network", "", "The Docker network from which to remove the Dapr runtime")
UninstallCmd.Flags().StringVarP(&uninstallNamespace, "namespace", "n", "dapr-system", "The Kubernetes namespace to uninstall Dapr from")
UninstallCmd.Flags().BoolP("help", "h", false, "Print this help message")
UninstallCmd.Flags().StringVarP(&uninstallContainerRuntime, "container-runtime", "", "docker", "The container runtime to use (defaults to docker)")
UninstallCmd.Flags().StringVarP(&uninstallContainerRuntime, "container-runtime", "", "docker", "The container runtime to use. Supported values are docker (default) and podman")
RootCmd.AddCommand(UninstallCmd)
}

View File

@ -25,8 +25,9 @@ import (
)
var (
upgradeRuntimeVersion string
upgradeImageVariant string
upgradeRuntimeVersion string
upgradeImageVariant string
upgradeDashboardVersion string
)
var UpgradeCmd = &cobra.Command{
@ -58,6 +59,7 @@ dapr upgrade -k
}
err = kubernetes.Upgrade(kubernetes.UpgradeConfig{
RuntimeVersion: upgradeRuntimeVersion,
DashboardVersion: upgradeDashboardVersion,
Args: values,
Timeout: timeout,
ImageRegistryURI: imageRegistryURI,
@ -78,6 +80,7 @@ func init() {
UpgradeCmd.Flags().BoolVarP(&kubernetesMode, "kubernetes", "k", false, "Upgrade or downgrade Dapr in a Kubernetes cluster")
UpgradeCmd.Flags().UintVarP(&timeout, "timeout", "", 300, "The timeout for the Kubernetes upgrade")
UpgradeCmd.Flags().StringVarP(&upgradeRuntimeVersion, "runtime-version", "", "", "The version of the Dapr runtime to upgrade or downgrade to, for example: 1.0.0")
UpgradeCmd.Flags().StringVarP(&upgradeDashboardVersion, "dashboard-version", "", "", "The version of the Dapr dashboard to upgrade or downgrade to, for example: 0.13.0")
UpgradeCmd.Flags().BoolP("help", "h", false, "Print this help message")
UpgradeCmd.Flags().StringArrayVar(&values, "set", []string{}, "set values on the command line (can specify multiple or separate values with commas: key1=val1,key2=val2)")
UpgradeCmd.Flags().String("image-registry", "", "Custom/Private docker image repository URL")

View File

@ -29,7 +29,7 @@ var output string
var VersionCmd = &cobra.Command{
Use: "version",
Short: "Print Dapr runtime and Cli version.",
Short: "Print the Dapr runtime and CLI version",
Example: `
# Version for Dapr
dapr version --output json

View File

@ -0,0 +1,16 @@
## Using with `docker-in-docker` feature
Since the Dapr CLI requires Docker, an easy way to get started is to use the `docker-in-docker` feature. This will install a separate Docker daemon inside the container for `dapr` to use:
```jsonc
"features": {
// Install the Dapr CLI
"ghcr.io/dapr/cli/dapr-cli:0": {},
// Enable Docker (via Docker-in-Docker)
"ghcr.io/devcontainers/features/docker-in-docker:2": {},
// Alternatively, use Docker-outside-of-Docker (uses Docker in the host)
//"ghcr.io/devcontainers/features/docker-outside-of-docker:1": {},
}
```
For more details on setting up a Dev Container with Dapr, see the [Developing Dapr applications with Dev Containers docs](https://docs.dapr.io/developing-applications/local-development/ides/vscode/vscode-remote-dev-containers/).

View File

@ -0,0 +1,39 @@
# dapr-cli (dapr-cli)
Install the Dapr CLI
## Example Usage
```json
"features": {
"ghcr.io/dapr/cli/dapr-cli:0": {}
}
```
## Options
| Options Id | Description | Type | Default Value |
|-----|-----|-----|-----|
| version | Version of the Dapr CLI to install (or "latest") | string | latest |
## Using with `docker-in-docker` feature
Since the Dapr CLI requires Docker, an easy way to get started is to use the `docker-in-docker` feature. This will install a separate Docker daemon inside the container for `dapr` to use:
```jsonc
"features": {
// Install the Dapr CLI
"ghcr.io/dapr/cli/dapr-cli:0": {},
// Enable Docker (via Docker-in-Docker)
"ghcr.io/devcontainers/features/docker-in-docker:2": {},
// Alternatively, use Docker-outside-of-Docker (uses Docker in the host)
//"ghcr.io/devcontainers/features/docker-outside-of-docker:1": {},
}
```
For more details on setting up a Dev Container with Dapr, see the [Developing Dapr applications with Dev Containers docs](https://docs.dapr.io/developing-applications/local-development/ides/vscode/vscode-remote-dev-containers/).
---
_Note: This file was auto-generated from the [devcontainer-feature.json](https://github.com/dapr/cli/blob/master/dev-container-feature/src/dapr-cli/devcontainer-feature.json). Add additional notes to a `NOTES.md`._

View File

@ -0,0 +1,16 @@
{
"name": "dapr-cli",
"id": "dapr-cli",
"version": "0.1.0",
"description": "Install the Dapr CLI",
"options": {
"version": {
"type": "string",
"proposals": [
"latest"
],
"default": "latest",
"description": "Version of the Dapr CLI to install (or \"latest\")"
}
}
}

View File

@ -0,0 +1,65 @@
#!/bin/sh
set -e
###################
# Helper Functions
###################
# Re-used from https://github.com/devcontainers/features/blob/4a9929f96485061e3778b35848e21d7c3c193480/src/dotnet/install.sh#L74
apt_get_update()
{
if [ "$(find /var/lib/apt/lists/* | wc -l)" = "0" ]; then
echo "Running apt-get update..."
apt-get update -y
fi
}
# Check if packages are installed and installs them if not.
check_packages() {
if ! dpkg -s "$@" > /dev/null 2>&1; then
apt_get_update
apt-get -y install --no-install-recommends "$@"
fi
}
get_latest_release() {
curl --silent "https://api.github.com/repos/dapr/cli/releases/latest" |
grep '"tag_name":' | sed -E "s/.*\"v([^\"]+)\".*/\1/"
}
###################
# Install Dapr CLI
###################
echo "Activating feature 'dapr-cli'"
check_packages curl ca-certificates
VERSION=${VERSION:-"latest"}
if [ "${VERSION}" = "latest" ]; then
VERSION=$(get_latest_release)
fi
ARCH=$(uname -m)
case $ARCH in
armv7*) ARCH="arm";;
aarch64) ARCH="arm64";;
x86_64) ARCH="amd64";;
esac
curl -SsL "https://github.com/dapr/cli/releases/download/v${VERSION}/dapr_linux_${ARCH}.tar.gz" | \
tar -zx -C /usr/local/bin dapr
dapr --version
## Write bash completion code to a file and source it from .bash_profile
mkdir -p $_REMOTE_USER_HOME/.dapr
dapr completion bash > $_REMOTE_USER_HOME/.dapr/completion.bash.inc
printf "
## dapr shell completion
source '$_REMOTE_USER_HOME/.dapr/completion.bash.inc'
" >> $_REMOTE_USER_HOME/.bashrc
chown -R $_REMOTE_USER:$_REMOTE_USER $_REMOTE_USER_HOME/.dapr
chown $_REMOTE_USER:$_REMOTE_USER $_REMOTE_USER_HOME/.bashrc

View File

@ -0,0 +1,44 @@
#!/bin/bash
# This test file will be executed against an auto-generated devcontainer.json that
# includes the 'dapr-cli' Feature with no options.
#
# For more information, see: https://github.com/devcontainers/cli/blob/main/docs/features/test.md
#
# Eg:
# {
# "image": "<..some-base-image...>",
# "features": {
# "dapr-cli": {}
# },
# "remoteUser": "root"
# }
#
# Thus, the value of all options will fall back to the default value in
# the Feature's 'devcontainer-feature.json'.
#
# These scripts are run as 'root' by default. Although that can be changed
# with the '--remote-user' flag.
#
# This test can be run with the following command (from the repo root folder):
#
# devcontainer features test \
# --features dapr-cli \
# --remote-user root \
# --skip-scenarios \
# --base-image mcr.microsoft.com/devcontainers/base:ubuntu \
# --project-folder dev-container-feature
set -e
# Optional: Import test library bundled with the devcontainer CLI
# Provides the 'check' and 'reportResults' commands.
source dev-container-features-test-lib
# Feature-specific tests
# The 'check' command comes from the dev-container-features-test-lib.
check "execute command" bash -c "dapr --help | grep 'Distributed Application Runtime'"
# Report results
# If any of the checks above exited with a non-zero exit code, the test will fail.
reportResults

View File

@ -7,7 +7,7 @@ This document helps you get started developing Dapr CLI. If you find any problem
### Linux and MacOS
1. The Go language environment `1.19` [(instructions)](https://golang.org/doc/install#tarball).
1. The Go language environment `1.21` [(instructions)](https://golang.org/doc/install#tarball).
* Make sure that your GOPATH and PATH are configured correctly
```bash
export GOPATH=~/go

View File

@ -0,0 +1,45 @@
# Release Guide
This document describes how to release Dapr CLI along with associated artifacts.
## Prerequisites
Only the repository maintainers and release team are allowed to execute the below steps.
## Pre-release build
Pre-release build will be built from `release-<major>.<minor>` branch and versioned by git version tag suffix e.g. `-rc.0`, `-rc.1`, etc. This build is not released to users who use the latest stable version.
**Pre-release process**
1. Create a PR to update the `Dapr runtime` and `Dapr dashboard` pre-release versions in workflow and tests files wherever applicable, and merge the PR to master branch. For example, please take a look at this PR - https://github.com/dapr/cli/pull/1019. Please note that this PR is just for reference and only reflects the absolute minimum number of file changes. These versions update could lead to some other changes also.
2. Create branch `release-<major>.<minor>` from master and push the branch. e.g. `release-1.11`. You can use the github web UI to create the branch or use the following command.
```sh
$ git checkout master && git reset --hard upstream/master && git pull upstream master
$ git checkout -b release-1.11
$ git push upstream release-1.11
```
3. Add pre-release version tag (with suffix -rc.0 e.g. v1.11.0-rc.0) and push the tag.
```sh
$ git tag "v1.11.0-rc.0" -m "v1.11.0-rc.0"
$ git push upstream v1.11.0-rc.0
```
4. CI creates the new build artifacts.
5. Test and validate the functionalities with the specific version.
6. If there are regressions and bugs, fix them in release-* branch. e.g `release-1.11` branch.
7. Create new pre-release version tag (with suffix -rc.1, -rc.2, etc).
8. Repeat from 5 to 7 until all bugs are fixed.
## Release the stable version to users
> **Note**: Make sure stable versions of `dapr runtime` and `dapr dashboard` are released before releasing the CLI and update their references in workflow and tests files wherever applicable.
Once all bugs are fixed, stable version can be released. Create a new git version tag (without the suffix -rc.x e.g. v1.11.0) and push the tag. CI will create the new build artifacts and release them.
## Release Patch version
Work on the existing `release-<major>.<minor>` branch to release a patch version. Once all bugs are fixed, create a new patch version tag, such as `v1.11.1-rc.0`. After verifying the fixes on this pre-release, create a new git version tag such as `v1.11.1` and push the tag. CI will create the new build artifacts and release them.

373
go.mod
View File

@ -1,230 +1,245 @@
module github.com/dapr/cli
go 1.19
go 1.23.5
require (
github.com/Azure/go-autorest/autorest v0.11.27 // indirect
github.com/Azure/go-autorest/autorest/adal v0.9.18 // indirect
github.com/Masterminds/semver v1.5.0
github.com/Masterminds/semver/v3 v3.3.0
github.com/Pallinder/sillyname-go v0.0.0-20130730142914-97aeae9e6ba1
github.com/briandowns/spinner v1.6.1
github.com/dapr/dapr v1.9.0-rc.3
github.com/dapr/go-sdk v1.5.1-0.20221001032816-7bcbf27f5152
github.com/docker/docker v20.10.17+incompatible
github.com/fatih/color v1.13.0
github.com/gocarina/gocsv v0.0.0-20190426105157-2fc85fcf0c07
github.com/hashicorp/go-retryablehttp v0.5.4
github.com/hashicorp/go-version v1.3.0
github.com/mitchellh/go-ps v0.0.0-20190716172923-621e5597135b
github.com/nightlyone/lockfile v0.0.0-20180618180623-0ad87eef1443
github.com/briandowns/spinner v1.19.0
github.com/dapr/dapr v1.15.0-rc.3.0.20250107220753-e073759df4c1
github.com/dapr/go-sdk v1.11.0
github.com/dapr/kit v0.13.1-0.20241127165251-30e2c24840b4
github.com/docker/docker v25.0.6+incompatible
github.com/evanphx/json-patch/v5 v5.9.0
github.com/fatih/color v1.17.0
github.com/gocarina/gocsv v0.0.0-20220927221512-ad3251f9fa25
github.com/hashicorp/go-retryablehttp v0.7.7
github.com/hashicorp/go-version v1.6.0
github.com/kolesnikovae/go-winjob v1.0.0
github.com/mitchellh/go-ps v1.0.0
github.com/nightlyone/lockfile v1.0.0
github.com/olekukonko/tablewriter v0.0.5
github.com/phayes/freeport v0.0.0-20220201140144-74d24b5ae9f5
github.com/pkg/browser v0.0.0-20210115035449-ce105d075bb4
github.com/shirou/gopsutil v3.21.4+incompatible
github.com/spf13/cobra v1.5.0
github.com/spf13/viper v1.10.0
github.com/stretchr/testify v1.8.0
golang.org/x/sys v0.0.0-20220928140112-f11e5e49a4ec
github.com/pkg/browser v0.0.0-20240102092130-5ac0b6a4141c
github.com/shirou/gopsutil v3.21.11+incompatible
github.com/spf13/cobra v1.8.1
github.com/spf13/pflag v1.0.5
github.com/spf13/viper v1.13.0
github.com/stretchr/testify v1.10.0
golang.org/x/mod v0.22.0
golang.org/x/sys v0.28.0
gopkg.in/yaml.v2 v2.4.0
helm.sh/helm/v3 v3.9.4
k8s.io/api v0.24.2
k8s.io/apiextensions-apiserver v0.24.2
k8s.io/apimachinery v0.24.2
k8s.io/cli-runtime v0.24.2
k8s.io/client-go v0.24.2
helm.sh/helm/v3 v3.17.1
k8s.io/api v0.32.1
k8s.io/apiextensions-apiserver v0.32.1
k8s.io/apimachinery v0.32.1
k8s.io/cli-runtime v0.32.1
k8s.io/client-go v0.32.1
k8s.io/helm v2.16.10+incompatible
sigs.k8s.io/yaml v1.3.0
sigs.k8s.io/yaml v1.4.0
)
require github.com/evanphx/json-patch v4.12.0+incompatible
require (
cloud.google.com/go/compute v1.5.0 // indirect
contrib.go.opencensus.io/exporter/prometheus v0.4.1 // indirect
github.com/AdhityaRamadhanus/fasthttpcors v0.0.0-20170121111917-d4c07198763a // indirect
github.com/Azure/go-ansiterm v0.0.0-20210617225240-d185dfc1b5a1 // indirect
github.com/Azure/go-autorest v14.2.0+incompatible // indirect
github.com/Azure/go-autorest/autorest/date v0.3.0 // indirect
github.com/Azure/go-autorest/logger v0.2.1 // indirect
github.com/Azure/go-autorest/tracing v0.6.0 // indirect
github.com/BurntSushi/toml v1.0.0 // indirect
github.com/MakeNowJust/heredoc v0.0.0-20170808103936-bb23615498cd // indirect
cel.dev/expr v0.18.0 // indirect
contrib.go.opencensus.io/exporter/prometheus v0.4.2 // indirect
dario.cat/mergo v1.0.1 // indirect
github.com/AdaLogics/go-fuzz-headers v0.0.0-20230811130428-ced1acdcaa24 // indirect
github.com/Azure/go-ansiterm v0.0.0-20230124172434-306776ec8161 // indirect
github.com/BurntSushi/toml v1.4.0 // indirect
github.com/Code-Hex/go-generics-cache v1.3.1 // indirect
github.com/MakeNowJust/heredoc v1.0.0 // indirect
github.com/Masterminds/goutils v1.1.1 // indirect
github.com/Masterminds/semver/v3 v3.1.1 // indirect
github.com/Masterminds/sprig/v3 v3.2.2 // indirect
github.com/Masterminds/squirrel v1.5.3 // indirect
github.com/Microsoft/go-winio v0.5.1 // indirect
github.com/Microsoft/hcsshim v0.9.3 // indirect
github.com/PuerkitoBio/purell v1.1.1 // indirect
github.com/PuerkitoBio/urlesc v0.0.0-20170810143723-de5bf2ad4578 // indirect
github.com/StackExchange/wmi v0.0.0-20210224194228-fe8f1750fd46 // indirect
github.com/andybalholm/brotli v1.0.4 // indirect
github.com/antlr/antlr4/runtime/Go/antlr v0.0.0-20210826220005-b48c857c3a0e // indirect
github.com/asaskevich/govalidator v0.0.0-20200428143746-21a406dcc535 // indirect
github.com/Masterminds/sprig/v3 v3.3.0 // indirect
github.com/Masterminds/squirrel v1.5.4 // indirect
github.com/Microsoft/go-winio v0.6.2 // indirect
github.com/PuerkitoBio/purell v1.2.1 // indirect
github.com/aavaz-ai/pii-scrubber v0.0.0-20220812094047-3fa450ab6973 // indirect
github.com/alphadose/haxmap v1.4.0 // indirect
github.com/anshal21/go-worker v1.1.0 // indirect
github.com/antlr4-go/antlr/v4 v4.13.0 // indirect
github.com/asaskevich/govalidator v0.0.0-20230301143203-a9d515a09cc2 // indirect
github.com/beorn7/perks v1.0.1 // indirect
github.com/cenkalti/backoff/v4 v4.1.3 // indirect
github.com/cespare/xxhash/v2 v2.1.2 // indirect
github.com/chai2010/gettext-go v0.0.0-20160711120539-c6fed771bfd5 // indirect
github.com/containerd/containerd v1.6.6 // indirect
github.com/containerd/continuity v0.2.2 // indirect
github.com/cyphar/filepath-securejoin v0.2.3 // indirect
github.com/dapr/components-contrib v1.9.0-rc.1 // indirect
github.com/dapr/kit v0.0.3-0.20220930182601-272e358ba6a7 // indirect
github.com/davecgh/go-spew v1.1.1 // indirect
github.com/docker/cli v20.10.17+incompatible // indirect
github.com/docker/distribution v2.8.1+incompatible // indirect
github.com/docker/docker-credential-helpers v0.6.4 // indirect
github.com/docker/go-connections v0.4.0 // indirect
github.com/blang/semver/v4 v4.0.0 // indirect
github.com/bufbuild/protocompile v0.6.0 // indirect
github.com/cenkalti/backoff/v4 v4.3.0 // indirect
github.com/cespare/xxhash/v2 v2.3.0 // indirect
github.com/chai2010/gettext-go v1.0.2 // indirect
github.com/chebyrash/promise v0.0.0-20230709133807-42ec49ba1459 // indirect
github.com/cloudevents/sdk-go/binding/format/protobuf/v2 v2.14.0 // indirect
github.com/cloudevents/sdk-go/v2 v2.15.2 // indirect
github.com/containerd/containerd v1.7.24 // indirect
github.com/containerd/errdefs v0.3.0 // indirect
github.com/containerd/log v0.1.0 // indirect
github.com/containerd/platforms v0.2.1 // indirect
github.com/cyphar/filepath-securejoin v0.3.6 // indirect
github.com/dapr/components-contrib v1.15.0-rc.1.0.20241216170750-aca5116d95c9 // indirect
github.com/dapr/durabletask-go v0.5.1-0.20241216172832-16da3e7c3530 // indirect
github.com/davecgh/go-spew v1.1.2-0.20180830191138-d8f796af33cc // indirect
github.com/decred/dcrd/dcrec/secp256k1/v4 v4.2.0 // indirect
github.com/distribution/reference v0.6.0 // indirect
github.com/dlclark/regexp2 v1.10.0 // indirect
github.com/docker/cli v25.0.1+incompatible // indirect
github.com/docker/distribution v2.8.3+incompatible // indirect
github.com/docker/docker-credential-helpers v0.7.0 // indirect
github.com/docker/go-connections v0.5.0 // indirect
github.com/docker/go-metrics v0.0.1 // indirect
github.com/docker/go-units v0.4.0 // indirect
github.com/emicklei/go-restful/v3 v3.8.0 // indirect
github.com/exponent-io/jsonpath v0.0.0-20151013193312-d6023ce2651d // indirect
github.com/fasthttp/router v1.4.12 // indirect
github.com/fsnotify/fsnotify v1.5.4 // indirect
github.com/ghodss/yaml v1.0.0 // indirect
github.com/go-errors/errors v1.4.0 // indirect
github.com/go-gorp/gorp/v3 v3.0.2 // indirect
github.com/go-kit/log v0.2.0 // indirect
github.com/go-logfmt/logfmt v0.5.1 // indirect
github.com/go-logr/logr v1.2.3 // indirect
github.com/docker/go-units v0.5.0 // indirect
github.com/emicklei/go-restful/v3 v3.11.0 // indirect
github.com/evanphx/json-patch v5.9.0+incompatible // indirect
github.com/exponent-io/jsonpath v0.0.0-20210407135951-1de76d718b3f // indirect
github.com/felixge/httpsnoop v1.0.4 // indirect
github.com/fsnotify/fsnotify v1.7.0 // indirect
github.com/fxamacker/cbor/v2 v2.7.0 // indirect
github.com/ghodss/yaml v1.0.1-0.20190212211648-25d852aebe32 // indirect
github.com/go-chi/chi/v5 v5.1.0 // indirect
github.com/go-chi/cors v1.2.1 // indirect
github.com/go-errors/errors v1.4.2 // indirect
github.com/go-gorp/gorp/v3 v3.1.0 // indirect
github.com/go-kit/log v0.2.1 // indirect
github.com/go-logfmt/logfmt v0.6.0 // indirect
github.com/go-logr/logr v1.4.2 // indirect
github.com/go-logr/stdr v1.2.2 // indirect
github.com/go-ole/go-ole v1.2.5 // indirect
github.com/go-openapi/jsonpointer v0.19.5 // indirect
github.com/go-openapi/jsonreference v0.19.5 // indirect
github.com/go-openapi/swag v0.19.14 // indirect
github.com/go-ole/go-ole v1.2.6 // indirect
github.com/go-openapi/jsonpointer v0.21.0 // indirect
github.com/go-openapi/jsonreference v0.20.2 // indirect
github.com/go-openapi/swag v0.23.0 // indirect
github.com/gobwas/glob v0.2.3 // indirect
github.com/goccy/go-json v0.10.2 // indirect
github.com/gogo/protobuf v1.3.2 // indirect
github.com/golang-jwt/jwt/v4 v4.2.0 // indirect
github.com/golang/groupcache v0.0.0-20210331224755-41bb18bfe9da // indirect
github.com/golang/mock v1.6.0 // indirect
github.com/golang/protobuf v1.5.2 // indirect
github.com/google/btree v1.0.1 // indirect
github.com/google/cel-go v0.10.1 // indirect
github.com/google/gnostic v0.5.7-v3refs // indirect
github.com/google/go-cmp v0.5.8 // indirect
github.com/golang/protobuf v1.5.4 // indirect
github.com/google/btree v1.1.3 // indirect
github.com/google/cel-go v0.22.0 // indirect
github.com/google/gnostic-models v0.6.8 // indirect
github.com/google/go-cmp v0.6.0 // indirect
github.com/google/gofuzz v1.2.0 // indirect
github.com/google/shlex v0.0.0-20191202100458-e7afc7fbc510 // indirect
github.com/google/uuid v1.3.0 // indirect
github.com/gorilla/mux v1.8.0 // indirect
github.com/google/uuid v1.6.0 // indirect
github.com/gorilla/mux v1.8.1 // indirect
github.com/gorilla/websocket v1.5.3 // indirect
github.com/gosuri/uitable v0.0.4 // indirect
github.com/gregjones/httpcache v0.0.0-20180305231024-9cad4c3443a7 // indirect
github.com/grpc-ecosystem/go-grpc-middleware v1.3.0 // indirect
github.com/grpc-ecosystem/grpc-gateway/v2 v2.7.0 // indirect
github.com/gregjones/httpcache v0.0.0-20190611155906-901d90724c79 // indirect
github.com/grpc-ecosystem/go-grpc-middleware v1.4.0 // indirect
github.com/grpc-ecosystem/grpc-gateway/v2 v2.22.0 // indirect
github.com/hashicorp/errwrap v1.1.0 // indirect
github.com/hashicorp/go-cleanhttp v0.5.2 // indirect
github.com/hashicorp/go-multierror v1.1.1 // indirect
github.com/hashicorp/golang-lru v0.5.4 // indirect
github.com/hashicorp/golang-lru/v2 v2.0.7 // indirect
github.com/hashicorp/hcl v1.0.0 // indirect
github.com/huandu/xstrings v1.3.2 // indirect
github.com/imdario/mergo v0.3.12 // indirect
github.com/inconshreveable/mousetrap v1.0.0 // indirect
github.com/jhump/protoreflect v1.13.0 // indirect
github.com/jmoiron/sqlx v1.3.5 // indirect
github.com/huandu/xstrings v1.5.0 // indirect
github.com/inconshreveable/mousetrap v1.1.0 // indirect
github.com/jhump/protoreflect v1.15.3 // indirect
github.com/jmoiron/sqlx v1.4.0 // indirect
github.com/josharian/intern v1.0.0 // indirect
github.com/json-iterator/go v1.1.12 // indirect
github.com/klauspost/compress v1.15.11 // indirect
github.com/klauspost/compress v1.17.10 // indirect
github.com/lann/builder v0.0.0-20180802200727-47ae307949d0 // indirect
github.com/lann/ps v0.0.0-20150810152359-62de8c46ede0 // indirect
github.com/lib/pq v1.10.6 // indirect
github.com/lestrrat-go/blackmagic v1.0.2 // indirect
github.com/lestrrat-go/httpcc v1.0.1 // indirect
github.com/lestrrat-go/httprc v1.0.5 // indirect
github.com/lestrrat-go/iter v1.0.2 // indirect
github.com/lestrrat-go/jwx/v2 v2.0.21 // indirect
github.com/lestrrat-go/option v1.0.1 // indirect
github.com/lib/pq v1.10.9 // indirect
github.com/liggitt/tabwriter v0.0.0-20181228230101-89fcab3d43de // indirect
github.com/magiconair/properties v1.8.6 // indirect
github.com/mailru/easyjson v0.7.6 // indirect
github.com/magiconair/properties v1.8.7 // indirect
github.com/mailru/easyjson v0.7.7 // indirect
github.com/marusama/semaphore/v2 v2.5.0 // indirect
github.com/mattn/go-colorable v0.1.13 // indirect
github.com/mattn/go-isatty v0.0.16 // indirect
github.com/mattn/go-isatty v0.0.20 // indirect
github.com/mattn/go-runewidth v0.0.9 // indirect
github.com/matttproud/golang_protobuf_extensions v1.0.2-0.20181231171920-c182affec369 // indirect
github.com/minio/blake2b-simd v0.0.0-20160723061019-3f5f724cb5b1 // indirect
github.com/mitchellh/copystructure v1.2.0 // indirect
github.com/mitchellh/go-wordwrap v1.0.0 // indirect
github.com/mitchellh/go-wordwrap v1.0.1 // indirect
github.com/mitchellh/mapstructure v1.5.1-0.20220423185008-bf980b35cac4 // indirect
github.com/mitchellh/reflectwalk v1.0.2 // indirect
github.com/moby/locker v1.0.1 // indirect
github.com/moby/spdystream v0.2.0 // indirect
github.com/moby/term v0.0.0-20210619224110-3f7ff695adc6 // indirect
github.com/moby/spdystream v0.5.0 // indirect
github.com/moby/term v0.5.0 // indirect
github.com/modern-go/concurrent v0.0.0-20180306012644-bacd9c7ef1dd // indirect
github.com/modern-go/reflect2 v1.0.2 // indirect
github.com/monochromegane/go-gitignore v0.0.0-20200626010858-205db1a8cc00 // indirect
github.com/morikuni/aec v1.0.0 // indirect
github.com/munnerz/goautoneg v0.0.0-20191010083416-a7dc8b61c822 // indirect
github.com/mxk/go-flowrate v0.0.0-20140419014527-cca7078d478f // indirect
github.com/opencontainers/go-digest v1.0.0 // indirect
github.com/opencontainers/image-spec v1.0.3-0.20211202183452-c5a74bcca799 // indirect
github.com/opencontainers/runc v1.1.2 // indirect
github.com/openzipkin/zipkin-go v0.4.0 // indirect
github.com/pelletier/go-toml v1.9.4 // indirect
github.com/opencontainers/image-spec v1.1.0 // indirect
github.com/openzipkin/zipkin-go v0.4.2 // indirect
github.com/panjf2000/ants/v2 v2.8.1 // indirect
github.com/pelletier/go-toml v1.9.5 // indirect
github.com/pelletier/go-toml/v2 v2.0.9 // indirect
github.com/peterbourgon/diskv v2.0.1+incompatible // indirect
github.com/pkg/errors v0.9.1 // indirect
github.com/pmezard/go-difflib v1.0.0 // indirect
github.com/prometheus/client_golang v1.12.2 // indirect
github.com/prometheus/client_model v0.2.0 // indirect
github.com/prometheus/common v0.35.0 // indirect
github.com/prometheus/procfs v0.7.3 // indirect
github.com/prometheus/statsd_exporter v0.22.3 // indirect
github.com/rubenv/sql-migrate v1.1.1 // indirect
github.com/russross/blackfriday v2.0.0+incompatible // indirect
github.com/savsgio/gotils v0.0.0-20220530130905-52f3993e8d6d // indirect
github.com/shopspring/decimal v1.2.0 // indirect
github.com/sirupsen/logrus v1.9.0 // indirect
github.com/sony/gobreaker v0.4.2-0.20210216022020-dd874f9dd33b // indirect
github.com/spf13/afero v1.6.0 // indirect
github.com/spf13/cast v1.4.1 // indirect
github.com/pkoukk/tiktoken-go v0.1.6 // indirect
github.com/pmezard/go-difflib v1.0.1-0.20181226105442-5d4384ee4fb2 // indirect
github.com/prometheus/client_golang v1.20.4 // indirect
github.com/prometheus/client_model v0.6.1 // indirect
github.com/prometheus/common v0.59.1 // indirect
github.com/prometheus/procfs v0.15.1 // indirect
github.com/prometheus/statsd_exporter v0.22.7 // indirect
github.com/rubenv/sql-migrate v1.7.1 // indirect
github.com/russross/blackfriday/v2 v2.1.0 // indirect
github.com/segmentio/asm v1.2.0 // indirect
github.com/shopspring/decimal v1.4.0 // indirect
github.com/sirupsen/logrus v1.9.3 // indirect
github.com/sony/gobreaker v0.5.0 // indirect
github.com/sourcegraph/conc v0.3.0 // indirect
github.com/spf13/afero v1.8.2 // indirect
github.com/spf13/cast v1.7.0 // indirect
github.com/spf13/jwalterweatherman v1.1.0 // indirect
github.com/spf13/pflag v1.0.5 // indirect
github.com/stoewer/go-strcase v1.2.0 // indirect
github.com/stretchr/objx v0.4.0 // indirect
github.com/subosito/gotenv v1.2.0 // indirect
github.com/tklauser/go-sysconf v0.3.6 // indirect
github.com/tklauser/numcpus v0.2.2 // indirect
github.com/valyala/bytebufferpool v1.0.0 // indirect
github.com/valyala/fasthttp v1.40.0 // indirect
github.com/spiffe/go-spiffe/v2 v2.1.7 // indirect
github.com/stoewer/go-strcase v1.3.0 // indirect
github.com/subosito/gotenv v1.4.1 // indirect
github.com/tidwall/transform v0.0.0-20201103190739-32f242e2dbde // indirect
github.com/tklauser/go-sysconf v0.3.12 // indirect
github.com/tklauser/numcpus v0.6.1 // indirect
github.com/tmc/langchaingo v0.1.12 // indirect
github.com/x448/float16 v0.8.4 // indirect
github.com/xeipuuv/gojsonpointer v0.0.0-20190905194746-02993c407bfb // indirect
github.com/xeipuuv/gojsonreference v0.0.0-20180127040603-bd5ef7bd5415 // indirect
github.com/xeipuuv/gojsonschema v1.2.0 // indirect
github.com/xlab/treeprint v0.0.0-20181112141820-a009c3971eca // indirect
go.opencensus.io v0.23.0 // indirect
go.opentelemetry.io/otel v1.7.0 // indirect
go.opentelemetry.io/otel/exporters/otlp/internal/retry v1.7.0 // indirect
go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.7.0 // indirect
go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc v1.7.0 // indirect
go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp v1.7.0 // indirect
go.opentelemetry.io/otel/exporters/zipkin v1.7.0 // indirect
go.opentelemetry.io/otel/sdk v1.7.0 // indirect
go.opentelemetry.io/otel/trace v1.7.0 // indirect
go.opentelemetry.io/proto/otlp v0.16.0 // indirect
go.starlark.net v0.0.0-20200306205701-8dd3e2ee1dd5 // indirect
go.uber.org/atomic v1.9.0 // indirect
golang.org/x/crypto v0.0.0-20220926161630-eccd6366d1be // indirect
golang.org/x/net v0.0.0-20220927171203-f486391704dc // indirect
golang.org/x/oauth2 v0.0.0-20220309155454-6242fa91716a // indirect
golang.org/x/sync v0.0.0-20220601150217-0de741cfad7f // indirect
golang.org/x/term v0.0.0-20210927222741-03fcf44c2211 // indirect
golang.org/x/text v0.3.7 // indirect
golang.org/x/time v0.0.0-20220210224613-90d013bbcef8 // indirect
gomodules.xyz/jsonpatch/v2 v2.2.0 // indirect
google.golang.org/appengine v1.6.7 // indirect
google.golang.org/genproto v0.0.0-20220622171453-ea41d75dfa0f // indirect
google.golang.org/grpc v1.48.0 // indirect
google.golang.org/protobuf v1.28.0 // indirect
github.com/xlab/treeprint v1.2.0 // indirect
github.com/yusufpapurcu/wmi v1.2.3 // indirect
github.com/zeebo/errs v1.3.0 // indirect
go.mongodb.org/mongo-driver v1.14.0 // indirect
go.opencensus.io v0.24.0 // indirect
go.opentelemetry.io/contrib/instrumentation/net/http/otelhttp v0.54.0 // indirect
go.opentelemetry.io/otel v1.32.0 // indirect
go.opentelemetry.io/otel/exporters/otlp/otlptrace v1.30.0 // indirect
go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracegrpc v1.30.0 // indirect
go.opentelemetry.io/otel/exporters/otlp/otlptrace/otlptracehttp v1.26.0 // indirect
go.opentelemetry.io/otel/exporters/zipkin v1.26.0 // indirect
go.opentelemetry.io/otel/metric v1.32.0 // indirect
go.opentelemetry.io/otel/sdk v1.30.0 // indirect
go.opentelemetry.io/otel/trace v1.32.0 // indirect
go.opentelemetry.io/proto/otlp v1.3.1 // indirect
go.uber.org/multierr v1.11.0 // indirect
golang.org/x/crypto v0.31.0 // indirect
golang.org/x/exp v0.0.0-20241204233417-43b7b7cde48d // indirect
golang.org/x/net v0.33.0 // indirect
golang.org/x/oauth2 v0.23.0 // indirect
golang.org/x/sync v0.10.0 // indirect
golang.org/x/term v0.27.0 // indirect
golang.org/x/text v0.21.0 // indirect
golang.org/x/time v0.7.0 // indirect
google.golang.org/genproto/googleapis/api v0.0.0-20240924160255-9d4c2d233b61 // indirect
google.golang.org/genproto/googleapis/rpc v0.0.0-20241202173237-19429a94021a // indirect
google.golang.org/grpc v1.68.1 // indirect
google.golang.org/protobuf v1.35.2 // indirect
gopkg.in/evanphx/json-patch.v4 v4.12.0 // indirect
gopkg.in/inf.v0 v0.9.1 // indirect
gopkg.in/ini.v1 v1.66.2 // indirect
gopkg.in/ini.v1 v1.67.0 // indirect
gopkg.in/yaml.v3 v3.0.1 // indirect
k8s.io/apiserver v0.24.2 // indirect
k8s.io/component-base v0.24.2 // indirect
k8s.io/klog/v2 v2.60.1 // indirect
k8s.io/kube-openapi v0.0.0-20220627174259-011e075b9cb8 // indirect
k8s.io/kubectl v0.24.2 // indirect
k8s.io/utils v0.0.0-20220210201930-3a6ce19ff2f9 // indirect
oras.land/oras-go v1.2.0 // indirect
sigs.k8s.io/controller-runtime v0.11.0 // indirect
sigs.k8s.io/json v0.0.0-20211208200746-9f7c6b3444d2 // indirect
sigs.k8s.io/kustomize/api v0.11.4 // indirect
sigs.k8s.io/kustomize/kyaml v0.13.6 // indirect
sigs.k8s.io/structured-merge-diff/v4 v4.2.1 // indirect
)
replace (
github.com/Azure/go-autorest => github.com/Azure/go-autorest v14.2.0+incompatible
github.com/docker/distribution => github.com/docker/distribution v0.0.0-20191216044856-a8371794149d
github.com/docker/docker => github.com/moby/moby v17.12.0-ce-rc1.0.20200618181300-9dc6525e6118+incompatible
github.com/russross/blackfriday => github.com/russross/blackfriday v1.5.2
k8s.io/client => github.com/kubernetes-client/go v0.0.0-20190928040339-c757968c4c36
k8s.io/apiserver v0.32.1 // indirect
k8s.io/component-base v0.32.1 // indirect
k8s.io/klog/v2 v2.130.1 // indirect
k8s.io/kube-openapi v0.0.0-20241105132330-32ad38e42d3f // indirect
k8s.io/kubectl v0.32.1 // indirect
k8s.io/utils v0.0.0-20241104100929-3ea5e8cea738 // indirect
oras.land/oras-go v1.2.5 // indirect
sigs.k8s.io/controller-runtime v0.19.0 // indirect
sigs.k8s.io/json v0.0.0-20241010143419-9aa6b5e7a4b3 // indirect
sigs.k8s.io/kustomize/api v0.18.0 // indirect
sigs.k8s.io/kustomize/kyaml v0.18.1 // indirect
sigs.k8s.io/structured-merge-diff/v4 v4.4.2 // indirect
)

1744
go.sum

File diff suppressed because it is too large Load Diff

View File

@ -141,7 +141,7 @@ if (!(Test-Path $zipFilePath -PathType Leaf)) {
Write-Output "Extracting $zipFilePath..."
Microsoft.Powershell.Archive\Expand-Archive -Force -Path $zipFilePath -DestinationPath $DaprRoot
if (!(Test-Path $DaprCliFilePath -PathType Leaf)) {
throw "Failed to download Dapr Cli archieve - $zipFilePath"
throw "Failed to download Dapr Cli archive - $zipFilePath"
}
# Check the Dapr CLI version

View File

@ -180,6 +180,7 @@ installFile() {
runAsRoot rm "$DAPR_CLI_FILE"
fi
chmod o+x $tmp_root_dapr_cli
mkdir -p $DAPR_INSTALL_DIR
runAsRoot cp "$tmp_root_dapr_cli" "$DAPR_INSTALL_DIR"
if [ -f "$DAPR_CLI_FILE" ]; then

View File

@ -9,7 +9,7 @@ import (
"strconv"
"strings"
jsonpatch "github.com/evanphx/json-patch"
jsonpatch "github.com/evanphx/json-patch/v5"
appsv1 "k8s.io/api/apps/v1"
batchv1 "k8s.io/api/batch/v1"
batchv1beta1 "k8s.io/api/batch/v1beta1"
@ -19,7 +19,7 @@ import (
yamlDecoder "k8s.io/apimachinery/pkg/util/yaml"
"sigs.k8s.io/yaml"
"github.com/dapr/dapr/pkg/injector/sidecar"
"github.com/dapr/dapr/pkg/injector/patcher"
)
const (
@ -55,8 +55,8 @@ const (
daprReadinessProbeThresholdKey = "dapr.io/sidecar-readiness-probe-threshold"
daprImageKey = "dapr.io/sidecar-image"
daprAppSSLKey = "dapr.io/app-ssl"
daprMaxRequestBodySizeKey = "dapr.io/http-max-request-size"
daprReadBufferSizeKey = "dapr.io/http-read-buffer-size"
daprMaxRequestBodySizeKey = "dapr.io/max-body-size"
daprReadBufferSizeKey = "dapr.io/read-buffer-size"
daprHTTPStreamRequestBodyKey = "dapr.io/http-stream-request-body"
daprGracefulShutdownSecondsKey = "dapr.io/graceful-shutdown-seconds"
daprEnableAPILoggingKey = "dapr.io/enable-api-logging"
@ -82,7 +82,7 @@ const (
)
type Annotator interface {
Annotate(io.Reader, io.Writer) error
Annotate(io.Reader, io.Writer) error //nolint: inamedparam
}
type K8sAnnotator struct {
@ -341,12 +341,8 @@ func (p *K8sAnnotator) annotateYAML(input []byte, config AnnotateOptions) ([]byt
}
// Create a patch operation for the annotations.
patchOps := []sidecar.PatchOperation{}
patchOps = append(patchOps, sidecar.PatchOperation{
Op: "add",
Path: path,
Value: annotations,
})
var patchOps []jsonpatch.Operation
patchOps = append(patchOps, patcher.NewPatchOperation("add", path, annotations))
patchBytes, err := json.Marshal(patchOps)
if err != nil {
return nil, false, err

View File

@ -2,11 +2,11 @@ package kubernetes
import (
"bytes"
"fmt"
"io"
"os"
"path"
"sort"
"strconv"
"strings"
"testing"
@ -333,7 +333,7 @@ func TestAnnotate(t *testing.T) {
for i := range expectedDocs {
if tt.printOutput {
t.Logf(outDocs[i])
t.Logf(outDocs[i]) //nolint:govet
}
assert.YAMLEq(t, expectedDocs[i], outDocs[i])
}
@ -423,7 +423,7 @@ func TestGetDaprAnnotations(t *testing.T) {
assert.Equal(t, "true", annotations[daprEnabledKey])
assert.Equal(t, appID, annotations[daprAppIDKey])
assert.Equal(t, fmt.Sprintf("%d", appPort), annotations[daprAppPortKey])
assert.Equal(t, strconv.Itoa(appPort), annotations[daprAppPortKey])
assert.Equal(t, config, annotations[daprConfigKey])
assert.Equal(t, appProtocol, annotations[daprAppProtocolKey])
assert.Equal(t, "true", annotations[daprEnableProfilingKey])
@ -431,31 +431,31 @@ func TestGetDaprAnnotations(t *testing.T) {
assert.Equal(t, apiTokenSecret, annotations[daprAPITokenSecretKey])
assert.Equal(t, appTokenSecret, annotations[daprAppTokenSecretKey])
assert.Equal(t, "true", annotations[daprLogAsJSONKey])
assert.Equal(t, fmt.Sprintf("%d", appMaxConcurrency), annotations[daprAppMaxConcurrencyKey])
assert.Equal(t, strconv.Itoa(appMaxConcurrency), annotations[daprAppMaxConcurrencyKey])
assert.Equal(t, "true", annotations[daprEnableMetricsKey])
assert.Equal(t, fmt.Sprintf("%d", metricsPort), annotations[daprMetricsPortKey])
assert.Equal(t, strconv.Itoa(metricsPort), annotations[daprMetricsPortKey])
assert.Equal(t, "true", annotations[daprEnableDebugKey])
assert.Equal(t, fmt.Sprintf("%d", debugPort), annotations[daprDebugPortKey])
assert.Equal(t, strconv.Itoa(debugPort), annotations[daprDebugPortKey])
assert.Equal(t, env, annotations[daprEnvKey])
assert.Equal(t, cpuLimit, annotations[daprCPULimitKey])
assert.Equal(t, memoryLimit, annotations[daprMemoryLimitKey])
assert.Equal(t, cpuRequest, annotations[daprCPURequestKey])
assert.Equal(t, memoryRequest, annotations[daprMemoryRequestKey])
assert.Equal(t, listenAddresses, annotations[daprListenAddressesKey])
assert.Equal(t, fmt.Sprintf("%d", livenessProbeDelay), annotations[daprLivenessProbeDelayKey])
assert.Equal(t, fmt.Sprintf("%d", livenessProbeTimeout), annotations[daprLivenessProbeTimeoutKey])
assert.Equal(t, fmt.Sprintf("%d", livenessProbePeriod), annotations[daprLivenessProbePeriodKey])
assert.Equal(t, fmt.Sprintf("%d", livenessProbeThreshold), annotations[daprLivenessProbeThresholdKey])
assert.Equal(t, fmt.Sprintf("%d", readinessProbeDelay), annotations[daprReadinessProbeDelayKey])
assert.Equal(t, fmt.Sprintf("%d", readinessProbeTimeout), annotations[daprReadinessProbeTimeoutKey])
assert.Equal(t, fmt.Sprintf("%d", readinessProbePeriod), annotations[daprReadinessProbePeriodKey])
assert.Equal(t, fmt.Sprintf("%d", readinessProbeThreshold), annotations[daprReadinessProbeThresholdKey])
assert.Equal(t, strconv.Itoa(livenessProbeDelay), annotations[daprLivenessProbeDelayKey])
assert.Equal(t, strconv.Itoa(livenessProbeTimeout), annotations[daprLivenessProbeTimeoutKey])
assert.Equal(t, strconv.Itoa(livenessProbePeriod), annotations[daprLivenessProbePeriodKey])
assert.Equal(t, strconv.Itoa(livenessProbeThreshold), annotations[daprLivenessProbeThresholdKey])
assert.Equal(t, strconv.Itoa(readinessProbeDelay), annotations[daprReadinessProbeDelayKey])
assert.Equal(t, strconv.Itoa(readinessProbeTimeout), annotations[daprReadinessProbeTimeoutKey])
assert.Equal(t, strconv.Itoa(readinessProbePeriod), annotations[daprReadinessProbePeriodKey])
assert.Equal(t, strconv.Itoa(readinessProbeThreshold), annotations[daprReadinessProbeThresholdKey])
assert.Equal(t, daprImage, annotations[daprImageKey])
assert.Equal(t, "true", annotations[daprAppSSLKey])
assert.Equal(t, fmt.Sprintf("%d", maxRequestBodySize), annotations[daprMaxRequestBodySizeKey])
assert.Equal(t, fmt.Sprintf("%d", readBufferSize), annotations[daprReadBufferSizeKey])
assert.Equal(t, strconv.Itoa(maxRequestBodySize), annotations[daprMaxRequestBodySizeKey])
assert.Equal(t, strconv.Itoa(readBufferSize), annotations[daprReadBufferSizeKey])
assert.Equal(t, "true", annotations[daprHTTPStreamRequestBodyKey])
assert.Equal(t, fmt.Sprintf("%d", gracefulShutdownSeconds), annotations[daprGracefulShutdownSecondsKey])
assert.Equal(t, strconv.Itoa(gracefulShutdownSeconds), annotations[daprGracefulShutdownSecondsKey])
assert.Equal(t, "true", annotations[daprEnableAPILoggingKey])
assert.Equal(t, unixDomainSocketPath, annotations[daprUnixDomainSocketPathKey])
assert.Equal(t, volumeMountsReadOnly, annotations[daprVolumeMountsReadOnlyKey])

View File

@ -18,6 +18,7 @@ import (
"sync"
k8s "k8s.io/client-go/kubernetes"
"k8s.io/client-go/rest"
"k8s.io/client-go/tools/clientcmd"
scheme "github.com/dapr/dapr/pkg/client/clientset/versioned"
@ -30,10 +31,6 @@ import (
// oidc auth
_ "k8s.io/client-go/plugin/pkg/client/auth/oidc"
// openstack auth
_ "k8s.io/client-go/plugin/pkg/client/auth/openstack"
"k8s.io/client-go/rest"
)
var (

View File

@ -15,6 +15,7 @@ package kubernetes
import (
"errors"
"fmt"
"strings"
"github.com/dapr/cli/utils"
@ -51,9 +52,14 @@ func GetDaprHelmChartName(helmConf *helm.Configuration) (string, error) {
if err != nil {
return "", err
}
if len(releases) == 0 {
return "", fmt.Errorf("could not find release name %q in your helm releases", daprReleaseName)
}
var chart string
for _, r := range releases {
if r.Chart != nil && strings.Contains(r.Chart.Name(), "dapr") {
if r.Chart != nil &&
strings.Contains(r.Chart.Name(), daprReleaseName) &&
!strings.Contains(r.Chart.Name(), dashboardReleaseName) {
chart = r.Name
break
}

View File

@ -25,6 +25,7 @@ import (
"github.com/dapr/cli/pkg/age"
"github.com/dapr/cli/utils"
v1alpha1 "github.com/dapr/dapr/pkg/apis/components/v1alpha1"
"github.com/dapr/dapr/pkg/client/clientset/versioned"
)
// ComponentsOutput represent a Dapr component.
@ -46,21 +47,37 @@ func PrintComponents(name, namespace, outputFormat string) error {
return nil, err
}
list, err := client.ComponentsV1alpha1().Components(namespace).List(meta_v1.ListOptions{})
// This means that the Dapr Components CRD is not installed and
// therefore no component items exist.
if apierrors.IsNotFound(err) {
list = &v1alpha1.ComponentList{
Items: []v1alpha1.Component{},
}
} else if err != nil {
return nil, err
}
return list, nil
return listComponents(client, namespace)
}, name, outputFormat)
}
func listComponents(client versioned.Interface, namespace string) (*v1alpha1.ComponentList, error) {
list, err := client.ComponentsV1alpha1().Components(namespace).List(meta_v1.ListOptions{})
// This means that the Dapr Components CRD is not installed and
// therefore no component items exist.
if apierrors.IsNotFound(err) {
list = &v1alpha1.ComponentList{
Items: []v1alpha1.Component{},
}
} else if err != nil {
return nil, err
}
return list, nil
}
func getComponent(client versioned.Interface, namespace string, componentName string) (*v1alpha1.Component, error) {
c, err := client.ComponentsV1alpha1().Components(namespace).Get(componentName, meta_v1.GetOptions{})
// This means that the Dapr Components CRD is not installed and
// therefore no component items exist.
if apierrors.IsNotFound(err) {
return &v1alpha1.Component{}, nil
} else if err != nil {
return nil, err
}
return c, err
}
func writeComponents(writer io.Writer, getConfigFunc func() (*v1alpha1.ComponentList, error), name, outputFormat string) error {
confs, err := getConfigFunc()
if err != nil {

View File

@ -15,7 +15,7 @@ package kubernetes
import (
"bytes"
"fmt"
"errors"
"testing"
"github.com/stretchr/testify/assert"
@ -139,7 +139,7 @@ func TestComponents(t *testing.T) {
name: "Yaml one config",
configName: "",
outputFormat: "yaml",
expectedOutput: "name: appConfig\nnamespace: \"\"\nspec:\n type: state.redis\n version: v1\n ignoreerrors: false\n metadata: []\n inittimeout: \"\"\n",
expectedOutput: "- name: appConfig\n namespace: \"\"\n spec:\n type: state.redis\n version: v1\n ignoreerrors: false\n metadata: []\n inittimeout: \"\"\n",
errString: "",
errorExpected: false,
k8sConfig: []v1alpha1.Component{
@ -189,7 +189,7 @@ func TestComponents(t *testing.T) {
name: "Json one config",
configName: "",
outputFormat: "json",
expectedOutput: "{\n \"name\": \"appConfig\",\n \"namespace\": \"\",\n \"spec\": {\n \"type\": \"state.redis\",\n \"version\": \"v1\",\n \"ignoreErrors\": false,\n \"metadata\": null,\n \"initTimeout\": \"\"\n }\n}",
expectedOutput: "[\n {\n \"name\": \"appConfig\",\n \"namespace\": \"\",\n \"spec\": {\n \"type\": \"state.redis\",\n \"version\": \"v1\",\n \"ignoreErrors\": false,\n \"metadata\": null,\n \"initTimeout\": \"\"\n }\n }\n]",
errString: "",
errorExpected: false,
k8sConfig: []v1alpha1.Component{
@ -242,7 +242,7 @@ func TestComponents(t *testing.T) {
err := writeComponents(&buff,
func() (*v1alpha1.ComponentList, error) {
if len(tc.errString) > 0 {
return nil, fmt.Errorf(tc.errString)
return nil, errors.New(tc.errString)
}
return &v1alpha1.ComponentList{Items: tc.k8sConfig}, nil

View File

@ -20,6 +20,7 @@ import (
"github.com/dapr/cli/utils"
v1alpha1 "github.com/dapr/dapr/pkg/apis/configuration/v1alpha1"
"github.com/dapr/kit/ptr"
)
func GetDefaultConfiguration() v1alpha1.Configuration {
@ -28,10 +29,10 @@ func GetDefaultConfiguration() v1alpha1.Configuration {
Name: "daprsystem",
},
Spec: v1alpha1.ConfigurationSpec{
MTLSSpec: v1alpha1.MTLSSpec{
Enabled: true,
WorkloadCertTTL: "24h",
AllowedClockSkew: "15m",
MTLSSpec: &v1alpha1.MTLSSpec{
Enabled: ptr.Of(true),
WorkloadCertTTL: ptr.Of("24h"),
AllowedClockSkew: ptr.Of("15m"),
},
},
}
@ -42,7 +43,7 @@ func GetDaprControlPlaneCurrentConfig() (*v1alpha1.Configuration, error) {
if err != nil {
return nil, err
}
output, err := utils.RunCmdAndWait("kubectl", "get", "configurations/daprsystem", "-n", namespace, "-o", "json")
output, err := utils.RunCmdAndWait("kubectl", "get", "configurations.dapr.io/daprsystem", "-n", namespace, "-o", "json")
if err != nil {
return nil, err
}

View File

@ -26,6 +26,7 @@ import (
"github.com/dapr/cli/pkg/age"
"github.com/dapr/cli/utils"
v1alpha1 "github.com/dapr/dapr/pkg/apis/configuration/v1alpha1"
"github.com/dapr/dapr/pkg/client/clientset/versioned"
)
type configurationsOutput struct {
@ -66,6 +67,18 @@ func PrintConfigurations(name, namespace, outputFormat string) error {
}, name, outputFormat)
}
func getDaprConfiguration(client versioned.Interface, namespace string, configurationName string) (*v1alpha1.Configuration, error) {
c, err := client.ConfigurationV1alpha1().Configurations(namespace).Get(configurationName, meta_v1.GetOptions{})
// This means that the Dapr Configurations CRD is not installed and
// therefore no configuration items exist.
if apierrors.IsNotFound(err) {
return &v1alpha1.Configuration{}, nil
} else if err != nil {
return nil, err
}
return c, err
}
func writeConfigurations(writer io.Writer, getConfigFunc func() (*v1alpha1.ConfigurationList, error), name, outputFormat string) error {
confs, err := getConfigFunc()
if err != nil {
@ -104,11 +117,15 @@ func writeConfigurations(writer io.Writer, getConfigFunc func() (*v1alpha1.Confi
func printConfigurationList(writer io.Writer, list []v1alpha1.Configuration) error {
co := []configurationsOutput{}
for _, c := range list {
var metricsEnabled bool
if c.Spec.MetricSpec != nil {
metricsEnabled = *c.Spec.MetricSpec.Enabled
}
co = append(co, configurationsOutput{
TracingEnabled: tracingEnabled(c.Spec.TracingSpec),
Name: c.GetName(),
Namespace: c.GetNamespace(),
MetricsEnabled: c.Spec.MetricSpec.Enabled,
MetricsEnabled: metricsEnabled,
Created: c.CreationTimestamp.Format("2006-01-02 15:04.05"),
Age: age.GetAge(c.CreationTimestamp.Time),
})
@ -121,7 +138,10 @@ func printConfigurationList(writer io.Writer, list []v1alpha1.Configuration) err
return utils.MarshalAndWriteTable(writer, co)
}
func tracingEnabled(spec v1alpha1.TracingSpec) bool {
func tracingEnabled(spec *v1alpha1.TracingSpec) bool {
if spec == nil {
return false
}
sr, err := strconv.ParseFloat(spec.SamplingRate, 32)
if err != nil {
return false

View File

@ -15,7 +15,7 @@ package kubernetes
import (
"bytes"
"fmt"
"errors"
"testing"
"github.com/stretchr/testify/assert"
@ -24,6 +24,7 @@ import (
v1alpha1 "github.com/dapr/dapr/pkg/apis/configuration/v1alpha1"
)
//nolint:dupword
func TestConfigurations(t *testing.T) {
now := meta_v1.Now()
formattedNow := now.Format("2006-01-02 15:04.05")
@ -129,7 +130,7 @@ func TestConfigurations(t *testing.T) {
name: "Yaml one config",
configName: "",
outputFormat: "yaml",
expectedOutput: "name: appConfig\nnamespace: default\nspec:\n apphttppipelinespec:\n handlers: []\n httppipelinespec:\n handlers: []\n tracingspec:\n samplingrate: \"\"\n stdout: false\n zipkin:\n endpointaddresss: \"\"\n otel:\n protocol: \"\"\n endpointAddress: \"\"\n isSecure: false\n metricspec:\n enabled: false\n mtlsspec:\n enabled: false\n workloadcertttl: \"\"\n allowedclockskew: \"\"\n secrets:\n scopes: []\n accesscontrolspec:\n defaultAction: \"\"\n trustDomain: \"\"\n policies: []\n nameresolutionspec:\n component: \"\"\n version: \"\"\n configuration:\n json:\n raw: []\n features: []\n apispec:\n allowed: []\n componentsspec: {}\n",
expectedOutput: "- name: appConfig\n namespace: default\n spec:\n apphttppipelinespec: null\n httppipelinespec: null\n tracingspec: null\n metricspec: null\n metricsspec: null\n mtlsspec: null\n secrets: null\n accesscontrolspec: null\n nameresolutionspec: null\n features: []\n apispec: null\n componentsspec: null\n loggingspec: null\n wasmspec: null\n workflowspec: null\n",
errString: "",
errorExpected: false,
k8sConfig: []v1alpha1.Configuration{
@ -147,7 +148,7 @@ func TestConfigurations(t *testing.T) {
name: "Yaml two configs",
configName: "",
outputFormat: "yaml",
expectedOutput: "- name: appConfig1\n namespace: default\n spec:\n apphttppipelinespec:\n handlers: []\n httppipelinespec:\n handlers: []\n tracingspec:\n samplingrate: \"\"\n stdout: false\n zipkin:\n endpointaddresss: \"\"\n otel:\n protocol: \"\"\n endpointAddress: \"\"\n isSecure: false\n metricspec:\n enabled: false\n mtlsspec:\n enabled: false\n workloadcertttl: \"\"\n allowedclockskew: \"\"\n secrets:\n scopes: []\n accesscontrolspec:\n defaultAction: \"\"\n trustDomain: \"\"\n policies: []\n nameresolutionspec:\n component: \"\"\n version: \"\"\n configuration:\n json:\n raw: []\n features: []\n apispec:\n allowed: []\n componentsspec: {}\n- name: appConfig2\n namespace: default\n spec:\n apphttppipelinespec:\n handlers: []\n httppipelinespec:\n handlers: []\n tracingspec:\n samplingrate: \"\"\n stdout: false\n zipkin:\n endpointaddresss: \"\"\n otel:\n protocol: \"\"\n endpointAddress: \"\"\n isSecure: false\n metricspec:\n enabled: false\n mtlsspec:\n enabled: false\n workloadcertttl: \"\"\n allowedclockskew: \"\"\n secrets:\n scopes: []\n accesscontrolspec:\n defaultAction: \"\"\n trustDomain: \"\"\n policies: []\n nameresolutionspec:\n component: \"\"\n version: \"\"\n configuration:\n json:\n raw: []\n features: []\n apispec:\n allowed: []\n componentsspec: {}\n",
expectedOutput: "- name: appConfig1\n namespace: default\n spec:\n apphttppipelinespec: null\n httppipelinespec: null\n tracingspec: null\n metricspec: null\n metricsspec: null\n mtlsspec: null\n secrets: null\n accesscontrolspec: null\n nameresolutionspec: null\n features: []\n apispec: null\n componentsspec: null\n loggingspec: null\n wasmspec: null\n workflowspec: null\n- name: appConfig2\n namespace: default\n spec:\n apphttppipelinespec: null\n httppipelinespec: null\n tracingspec: null\n metricspec: null\n metricsspec: null\n mtlsspec: null\n secrets: null\n accesscontrolspec: null\n nameresolutionspec: null\n features: []\n apispec: null\n componentsspec: null\n loggingspec: null\n wasmspec: null\n workflowspec: null\n",
errString: "",
errorExpected: false,
k8sConfig: []v1alpha1.Configuration{
@ -173,7 +174,7 @@ func TestConfigurations(t *testing.T) {
name: "Json one config",
configName: "",
outputFormat: "json",
expectedOutput: "{\n \"name\": \"appConfig\",\n \"namespace\": \"default\",\n \"spec\": {\n \"appHttpPipeline\": {\n \"handlers\": null\n },\n \"httpPipeline\": {\n \"handlers\": null\n },\n \"tracing\": {\n \"samplingRate\": \"\",\n \"stdout\": false,\n \"zipkin\": {\n \"endpointAddress\": \"\"\n },\n \"otel\": {\n \"protocol\": \"\",\n \"endpointAddress\": \"\",\n \"isSecure\": false\n }\n },\n \"metric\": {\n \"enabled\": false\n },\n \"mtls\": {\n \"enabled\": false,\n \"workloadCertTTL\": \"\",\n \"allowedClockSkew\": \"\"\n },\n \"secrets\": {\n \"scopes\": null\n },\n \"accessControl\": {\n \"defaultAction\": \"\",\n \"trustDomain\": \"\",\n \"policies\": null\n },\n \"nameResolution\": {\n \"component\": \"\",\n \"version\": \"\",\n \"configuration\": null\n },\n \"api\": {},\n \"components\": {}\n }\n}",
expectedOutput: "[\n {\n \"name\": \"appConfig\",\n \"namespace\": \"default\",\n \"spec\": {}\n }\n]",
errString: "",
errorExpected: false,
k8sConfig: []v1alpha1.Configuration{
@ -191,7 +192,7 @@ func TestConfigurations(t *testing.T) {
name: "Json two configs",
configName: "",
outputFormat: "json",
expectedOutput: "[\n {\n \"name\": \"appConfig1\",\n \"namespace\": \"default\",\n \"spec\": {\n \"appHttpPipeline\": {\n \"handlers\": null\n },\n \"httpPipeline\": {\n \"handlers\": null\n },\n \"tracing\": {\n \"samplingRate\": \"\",\n \"stdout\": false,\n \"zipkin\": {\n \"endpointAddress\": \"\"\n },\n \"otel\": {\n \"protocol\": \"\",\n \"endpointAddress\": \"\",\n \"isSecure\": false\n }\n },\n \"metric\": {\n \"enabled\": false\n },\n \"mtls\": {\n \"enabled\": false,\n \"workloadCertTTL\": \"\",\n \"allowedClockSkew\": \"\"\n },\n \"secrets\": {\n \"scopes\": null\n },\n \"accessControl\": {\n \"defaultAction\": \"\",\n \"trustDomain\": \"\",\n \"policies\": null\n },\n \"nameResolution\": {\n \"component\": \"\",\n \"version\": \"\",\n \"configuration\": null\n },\n \"api\": {},\n \"components\": {}\n }\n },\n {\n \"name\": \"appConfig2\",\n \"namespace\": \"default\",\n \"spec\": {\n \"appHttpPipeline\": {\n \"handlers\": null\n },\n \"httpPipeline\": {\n \"handlers\": null\n },\n \"tracing\": {\n \"samplingRate\": \"\",\n \"stdout\": false,\n \"zipkin\": {\n \"endpointAddress\": \"\"\n },\n \"otel\": {\n \"protocol\": \"\",\n \"endpointAddress\": \"\",\n \"isSecure\": false\n }\n },\n \"metric\": {\n \"enabled\": false\n },\n \"mtls\": {\n \"enabled\": false,\n \"workloadCertTTL\": \"\",\n \"allowedClockSkew\": \"\"\n },\n \"secrets\": {\n \"scopes\": null\n },\n \"accessControl\": {\n \"defaultAction\": \"\",\n \"trustDomain\": \"\",\n \"policies\": null\n },\n \"nameResolution\": {\n \"component\": \"\",\n \"version\": \"\",\n \"configuration\": null\n },\n \"api\": {},\n \"components\": {}\n }\n }\n]",
expectedOutput: "[\n {\n \"name\": \"appConfig1\",\n \"namespace\": \"default\",\n \"spec\": {}\n },\n {\n \"name\": \"appConfig2\",\n \"namespace\": \"default\",\n \"spec\": {}\n }\n]",
errString: "",
errorExpected: false,
k8sConfig: []v1alpha1.Configuration{
@ -220,7 +221,7 @@ func TestConfigurations(t *testing.T) {
err := writeConfigurations(&buff,
func() (*v1alpha1.ConfigurationList, error) {
if len(tc.errString) > 0 {
return nil, fmt.Errorf(tc.errString)
return nil, errors.New(tc.errString)
}
return &v1alpha1.ConfigurationList{Items: tc.k8sConfig}, nil

View File

@ -1,8 +1,5 @@
//go:build !windows
// +build !windows
/*
Copyright 2021 The Dapr Authors
Copyright 2023 The Dapr Authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
@ -14,14 +11,23 @@ See the License for the specific language governing permissions and
limitations under the License.
*/
package cmd
package kubernetes
import (
"os"
"os/signal"
"syscall"
)
import "github.com/Masterminds/semver/v3"
func setupShutdownNotify(sigCh chan os.Signal) {
signal.Notify(sigCh, syscall.SIGTERM, syscall.SIGINT)
const daprHelmChartWithDashboard = "<= 1.10.x"
// IsDashboardIncluded returns true if dashboard is included in Helm chart version for Dapr.
func IsDashboardIncluded(runtimeVersion string) (bool, error) {
c, err := semver.NewConstraint(daprHelmChartWithDashboard)
if err != nil {
return false, err
}
v, err := semver.NewVersion(runtimeVersion)
if err != nil {
return false, err
}
return c.Check(v), nil
}

View File

@ -0,0 +1,81 @@
/*
Copyright 2023 The Dapr Authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package kubernetes
import (
"testing"
"github.com/stretchr/testify/assert"
)
func TestDashboardChart(t *testing.T) {
testCases := []struct {
runtimeVersion string
expectDashboard bool
expectError bool
}{
{
runtimeVersion: "1.9.6",
expectDashboard: true,
expectError: false,
},
{
runtimeVersion: "1.10.7",
expectDashboard: true,
expectError: false,
},
{
runtimeVersion: "1.10.99",
expectDashboard: true,
expectError: false,
},
{
runtimeVersion: "1.11.0",
expectDashboard: false,
expectError: false,
},
{
runtimeVersion: "1.11.0",
expectDashboard: false,
expectError: false,
},
{
runtimeVersion: "1.12.7",
expectDashboard: false,
expectError: false,
},
{
runtimeVersion: "1.13.0",
expectDashboard: false,
expectError: false,
},
{
runtimeVersion: "Bad Version",
expectDashboard: false,
expectError: true,
},
}
for _, tc := range testCases {
t.Run("Validating version "+tc.runtimeVersion, func(t *testing.T) {
hasDashboard, err := IsDashboardIncluded(tc.runtimeVersion)
if tc.expectError {
assert.Error(t, err, "expected an error")
} else {
assert.NoError(t, err, "expected an error")
}
assert.Equal(t, tc.expectDashboard, hasDashboard, "dashboard expectation")
})
}
}

View File

@ -33,37 +33,117 @@ import (
"github.com/dapr/cli/pkg/print"
cli_ver "github.com/dapr/cli/pkg/version"
"github.com/dapr/cli/utils"
"github.com/dapr/dapr/pkg/client/clientset/versioned"
)
const (
daprReleaseName = "dapr"
daprHelmRepo = "https://dapr.github.io/helm-charts"
latestVersion = "latest"
daprReleaseName = "dapr"
dashboardReleaseName = "dapr-dashboard"
latestVersion = "latest"
bitnamiStableVersion = "17.14.5"
// dev mode constants.
thirdPartyDevNamespace = "default"
zipkinChartName = "zipkin"
redisChartName = "redis"
zipkinReleaseName = "dapr-dev-zipkin"
redisReleaseName = "dapr-dev-redis"
redisVersion = "6.2.11"
bitnamiHelmRepo = "https://charts.bitnami.com/bitnami"
daprHelmRepo = "https://dapr.github.io/helm-charts"
zipkinHelmRepo = "https://openzipkin.github.io/zipkin"
stateStoreComponentName = "statestore"
pubsubComponentName = "pubsub"
zipkingConfigurationName = "appconfig"
)
type InitConfiguration struct {
Version string
Namespace string
EnableMTLS bool
EnableHA bool
Args []string
Wait bool
Timeout uint
ImageRegistryURI string
ImageVariant string
Version string
DashboardVersion string
Namespace string
EnableMTLS bool
EnableHA bool
EnableDev bool
Args []string
Wait bool
Timeout uint
ImageRegistryURI string
ImageVariant string
RootCertificateFilePath string
IssuerCertificateFilePath string
IssuerPrivateKeyFilePath string
}
// Init deploys the Dapr operator using the supplied runtime version.
func Init(config InitConfiguration) error {
msg := "Deploying the Dapr control plane to your cluster..."
stopSpinning := print.Spinner(os.Stdout, msg)
defer stopSpinning(print.Failure)
if err := install(config); err != nil {
helmRepoDapr := utils.GetEnv("DAPR_HELM_REPO_URL", daprHelmRepo)
err := installWithConsole(daprReleaseName, config.Version, helmRepoDapr, "Dapr control plane", config)
if err != nil {
return err
}
stopSpinning(print.Success)
for _, dashboardClusterRole := range []string{"dashboard-reader", "dapr-dashboard"} {
// Detect Dapr Dashboard using a cluster-level resource (not dependent on namespace).
_, err = utils.RunCmdAndWait("kubectl", "describe", "clusterrole", dashboardClusterRole)
if err == nil {
// No need to install Dashboard since it is already present.
// Charts for versions < 1.11 contain Dashboard already.
return nil
}
}
err = installWithConsole(dashboardReleaseName, config.DashboardVersion, helmRepoDapr, "Dapr dashboard", config)
if err != nil {
return err
}
if config.EnableDev {
redisChartVals := []string{
"image.tag=" + redisVersion,
"replica.replicaCount=0",
}
err = installThirdPartyWithConsole(redisReleaseName, redisChartName, bitnamiStableVersion, bitnamiHelmRepo, "Dapr Redis", redisChartVals, config)
if err != nil {
return err
}
err = installThirdPartyWithConsole(zipkinReleaseName, zipkinChartName, latestVersion, zipkinHelmRepo, "Dapr Zipkin", []string{}, config)
if err != nil {
return err
}
err = initDevConfigs()
if err != nil {
return err
}
}
return nil
}
func installThirdPartyWithConsole(releaseName, chartName, releaseVersion, helmRepo string, prettyName string, chartValues []string, config InitConfiguration) error {
installSpinning := print.Spinner(os.Stdout, "Deploying the "+prettyName+" with "+releaseVersion+" version to your cluster...")
defer installSpinning(print.Failure)
// releaseVersion of chart will always be latest version.
err := installThirdParty(releaseName, chartName, releaseVersion, helmRepo, chartValues, config)
if err != nil {
return err
}
installSpinning(print.Success)
return nil
}
func installWithConsole(releaseName, releaseVersion, helmRepo string, prettyName string, config InitConfiguration) error {
installSpinning := print.Spinner(os.Stdout, "Deploying the "+prettyName+" with "+releaseVersion+" version to your cluster...")
defer installSpinning(print.Failure)
err := install(releaseName, releaseVersion, helmRepo, config)
if err != nil {
return err
}
installSpinning(print.Success)
return nil
}
@ -93,16 +173,23 @@ func helmConfig(namespace string) (*helm.Configuration, error) {
return &ac, err
}
func getVersion(version string) (string, error) {
func getVersion(releaseName string, version string) (string, error) {
actualVersion := version
if version == latestVersion {
var err error
version, err = cli_ver.GetDaprVersion()
if releaseName == daprReleaseName {
actualVersion, err = cli_ver.GetDaprVersion()
} else if releaseName == dashboardReleaseName {
actualVersion, err = cli_ver.GetDashboardVersion()
} else {
return "", fmt.Errorf("cannot get latest version for unknown chart: %s", releaseName)
}
if err != nil {
return "", fmt.Errorf("cannot get the latest release version: %w", err)
}
version = strings.TrimPrefix(version, "v")
actualVersion = strings.TrimPrefix(actualVersion, "v")
}
return version, nil
return actualVersion, nil
}
func createTempDir() (string, error) {
@ -121,15 +208,15 @@ func locateChartFile(dirPath string) (string, error) {
return filepath.Join(dirPath, files[0].Name()), nil
}
func daprChart(version string, config *helm.Configuration) (*chart.Chart, error) {
func getHelmChart(version, releaseName, helmRepo string, config *helm.Configuration) (*chart.Chart, error) {
pull := helm.NewPullWithOpts(helm.WithConfig(config))
pull.RepoURL = utils.GetEnv("DAPR_HELM_REPO_URL", daprHelmRepo)
pull.RepoURL = helmRepo
pull.Username = utils.GetEnv("DAPR_HELM_REPO_USERNAME", "")
pull.Password = utils.GetEnv("DAPR_HELM_REPO_PASSWORD", "")
pull.Settings = &cli.EnvSettings{}
if version != latestVersion {
if version != latestVersion && (releaseName == daprReleaseName || releaseName == dashboardReleaseName || releaseName == redisChartName) {
pull.Version = chartVersion(version)
}
@ -141,7 +228,7 @@ func daprChart(version string, config *helm.Configuration) (*chart.Chart, error)
pull.DestDir = dir
_, err = pull.Run(daprReleaseName)
_, err = pull.Run(releaseName)
if err != nil {
return nil, err
}
@ -153,23 +240,38 @@ func daprChart(version string, config *helm.Configuration) (*chart.Chart, error)
return loader.Load(chartPath)
}
func chartValues(config InitConfiguration) (map[string]interface{}, error) {
func daprChartValues(config InitConfiguration, version string) (map[string]interface{}, error) {
chartVals := map[string]interface{}{}
err := utils.ValidateImageVariant(config.ImageVariant)
if err != nil {
return nil, err
}
globalVals := []string{
helmVals := []string{
fmt.Sprintf("global.ha.enabled=%t", config.EnableHA),
fmt.Sprintf("global.mtls.enabled=%t", config.EnableMTLS),
fmt.Sprintf("global.tag=%s", utils.GetVariantVersion(config.Version, config.ImageVariant)),
"global.tag=" + utils.GetVariantVersion(version, config.ImageVariant),
}
if len(config.ImageRegistryURI) != 0 {
globalVals = append(globalVals, fmt.Sprintf("global.registry=%s", config.ImageRegistryURI))
helmVals = append(helmVals, "global.registry="+config.ImageRegistryURI)
}
globalVals = append(globalVals, config.Args...)
helmVals = append(helmVals, config.Args...)
for _, v := range globalVals {
if config.RootCertificateFilePath != "" && config.IssuerCertificateFilePath != "" && config.IssuerPrivateKeyFilePath != "" {
rootCertBytes, issuerCertBytes, issuerKeyBytes, err := parseCertificateFiles(
config.RootCertificateFilePath,
config.IssuerCertificateFilePath,
config.IssuerPrivateKeyFilePath,
)
if err != nil {
return nil, err
}
helmVals = append(helmVals, "dapr_sentry.tls.root.certPEM="+string(rootCertBytes),
"dapr_sentry.tls.issuer.certPEM="+string(issuerCertBytes),
"dapr_sentry.tls.issuer.keyPEM="+string(issuerKeyBytes),
)
}
for _, v := range helmVals {
if err := strvals.ParseInto(v, chartVals); err != nil {
return nil, err
}
@ -177,7 +279,7 @@ func chartValues(config InitConfiguration) (map[string]interface{}, error) {
return chartVals, nil
}
func install(config InitConfiguration) error {
func install(releaseName, releaseVersion, helmRepo string, config InitConfiguration) error {
err := createNamespace(config.Namespace)
if err != nil {
return err
@ -188,28 +290,30 @@ func install(config InitConfiguration) error {
return err
}
daprChart, err := daprChart(config.Version, helmConf)
daprChart, err := getHelmChart(releaseVersion, releaseName, helmRepo, helmConf)
if err != nil {
return err
}
version, err := getVersion(config.Version)
version, err := getVersion(releaseName, releaseVersion)
if err != nil {
return err
}
err = applyCRDs(fmt.Sprintf("v%s", version))
if err != nil {
return err
if releaseName == daprReleaseName {
err = applyCRDs("v" + version)
if err != nil {
return err
}
}
installClient := helm.NewInstall(helmConf)
installClient.ReleaseName = daprReleaseName
installClient.ReleaseName = releaseName
installClient.Namespace = config.Namespace
installClient.Wait = config.Wait
installClient.Timeout = time.Duration(config.Timeout) * time.Second
installClient.Timeout = time.Duration(config.Timeout) * time.Second //nolint:gosec
values, err := chartValues(config)
values, err := daprChartValues(config, version)
if err != nil {
return err
}
@ -217,15 +321,48 @@ func install(config InitConfiguration) error {
if _, err = installClient.Run(daprChart, values); err != nil {
return err
}
return nil
}
func installThirdParty(releaseName, chartName, releaseVersion, helmRepo string, chartVals []string, config InitConfiguration) error {
helmConf, err := helmConfig(thirdPartyDevNamespace)
if err != nil {
return err
}
helmChart, err := getHelmChart(releaseVersion, chartName, helmRepo, helmConf)
if err != nil {
return err
}
installClient := helm.NewInstall(helmConf)
installClient.ReleaseName = releaseName
installClient.Namespace = thirdPartyDevNamespace
installClient.Wait = config.Wait
installClient.Timeout = time.Duration(config.Timeout) * time.Second //nolint:gosec
values := map[string]interface{}{}
for _, val := range chartVals {
if err = strvals.ParseInto(val, values); err != nil {
return err
}
}
if _, err = installClient.Run(helmChart, values); err != nil {
return err
}
return nil
}
func debugLogf(format string, v ...interface{}) {
}
func confirmExist(cfg *helm.Configuration) (bool, error) {
func confirmExist(cfg *helm.Configuration, releaseName string) (bool, error) {
client := helm.NewGet(cfg)
release, err := client.Run(daprReleaseName)
release, err := client.Run(releaseName)
if release == nil {
return false, nil
@ -237,3 +374,164 @@ func confirmExist(cfg *helm.Configuration) (bool, error) {
return true, nil
}
func checkAndOverWriteFile(filePath string, b []byte) error {
_, err := os.Stat(filePath)
if os.IsNotExist(err) {
// #nosec G306
if err = os.WriteFile(filePath, b, 0o644); err != nil {
return err
}
}
return nil
}
func isComponentPresent(client versioned.Interface, namespace string, componentName string) (bool, error) {
c, err := getComponent(client, namespace, componentName)
if err != nil {
return false, err
}
return c.Name == componentName, err
}
func isConfigurationPresent(client versioned.Interface, namespace string, configurationName string) (bool, error) {
c, err := getDaprConfiguration(client, namespace, configurationName)
if err != nil {
return false, err
}
return c.Name == configurationName, nil
}
func initDevConfigs() error {
redisStatestore := `
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: statestore
spec:
type: state.redis
version: v1
metadata:
# These settings will work out of the box if you use helm install
# bitnami/redis. If you have your own setup, replace
# redis-master:6379 with your own Redis master address, and the
# Redis password with your own Secret's name. For more information,
# see https://docs.dapr.io/operations/components/component-secrets .
- name: redisHost
value: dapr-dev-redis-master:6379
- name: redisPassword
secretKeyRef:
name: dapr-dev-redis
key: redis-password
auth:
secretStore: kubernetes
`
redisPubsub := `
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: pubsub
spec:
type: pubsub.redis
version: v1
metadata:
# These settings will work out of the box if you use helm install
# bitnami/redis. If you have your own setup, replace
# redis-master:6379 with your own Redis master address, and the
# Redis password with your own Secret's name. For more information,
# see https://docs.dapr.io/operations/components/component-secrets .
- name: redisHost
value: dapr-dev-redis-master:6379
- name: redisPassword
secretKeyRef:
name: dapr-dev-redis
key: redis-password
auth:
secretStore: kubernetes
`
// This config needs to be named as appconfig, as it is used in later steps in `dapr run -f . -k`. See `pkg/kubernetes/run.go`.
zipkinConfig := `
apiVersion: dapr.io/v1alpha1
kind: Configuration
metadata:
name: appconfig
spec:
tracing:
samplingRate: "1"
zipkin:
endpointAddress: "http://dapr-dev-zipkin.default.svc.cluster.local:9411/api/v2/spans"
`
tempDirPath, err := createTempDir()
defer os.RemoveAll(tempDirPath)
if err != nil {
return err
}
client, err := DaprClient()
if err != nil {
return err
}
present, err := isComponentPresent(client, thirdPartyDevNamespace, stateStoreComponentName)
if present || err != nil {
if err != nil {
print.WarningStatusEvent(os.Stderr, "Error listing components, skipping default dev component creation.")
} else {
print.WarningStatusEvent(os.Stderr, "Component with name %q already present in namespace %q. Skipping component creation.", stateStoreComponentName, thirdPartyDevNamespace)
}
return err
}
redisPath := filepath.Join(tempDirPath, "redis-statestore.yaml")
err = checkAndOverWriteFile(redisPath, []byte(redisStatestore))
if err != nil {
return err
}
print.InfoStatusEvent(os.Stdout, "Applying %q component to Kubernetes %q namespace.", stateStoreComponentName, thirdPartyDevNamespace)
_, err = utils.RunCmdAndWait("kubectl", "apply", "-f", redisPath)
if err != nil {
return err
}
present, err = isComponentPresent(client, thirdPartyDevNamespace, pubsubComponentName)
if present || err != nil {
if err != nil {
print.WarningStatusEvent(os.Stderr, "Error listing components, skipping default dev component creation.")
} else {
print.WarningStatusEvent(os.Stderr, "Component with name %q already present in namespace %q. Skipping component creation.", pubsubComponentName, thirdPartyDevNamespace)
}
return err
}
redisPath = filepath.Join(tempDirPath, "redis-pubsub.yaml")
err = checkAndOverWriteFile(redisPath, []byte(redisPubsub))
if err != nil {
return err
}
print.InfoStatusEvent(os.Stdout, "Applying %q component to Kubernetes %q namespace.", pubsubComponentName, thirdPartyDevNamespace)
_, err = utils.RunCmdAndWait("kubectl", "apply", "-f", redisPath)
if err != nil {
return err
}
present, err = isConfigurationPresent(client, thirdPartyDevNamespace, zipkingConfigurationName)
if present || err != nil {
if err != nil {
print.WarningStatusEvent(os.Stderr, "Error listing configurations, skipping default dev configuration creation.")
} else {
print.WarningStatusEvent(os.Stderr, "Configuration with name %q already present in namespace %q. Skipping configuration creation.", zipkingConfigurationName, thirdPartyDevNamespace)
}
return err
}
zipkinPath := filepath.Join(tempDirPath, "zipkin-config.yaml")
err = checkAndOverWriteFile(zipkinPath, []byte(zipkinConfig))
if err != nil {
return err
}
print.InfoStatusEvent(os.Stdout, "Applying %q zipkin configuration to Kubernetes %q namespace.", zipkingConfigurationName, thirdPartyDevNamespace)
_, err = utils.RunCmdAndWait("kubectl", "apply", "-f", zipkinPath)
if err != nil {
return err
}
return nil
}

View File

@ -14,17 +14,32 @@ limitations under the License.
package kubernetes
import (
"bufio"
"context"
"errors"
"fmt"
"io"
"os"
"strings"
"time"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
v1 "k8s.io/client-go/kubernetes/typed/core/v1"
"github.com/dapr/cli/pkg/print"
)
const (
daprdContainerName = "daprd"
appIDContainerArgName = "--app-id"
// number of retries when trying to list pods for getting logs.
maxListingRetry = 10
// delay between retries of pod listing.
listingDelay = 200 * time.Microsecond
// delay before retrying for getting logs.
streamingDelay = 100 * time.Millisecond
)
// Logs fetches Dapr sidecar logs from Kubernetes.
@ -84,3 +99,98 @@ func Logs(appID, podName, namespace string) error {
return nil
}
// streamContainerLogsToDisk streams all containers logs for the given selector to a given disk directory.
func streamContainerLogsToDisk(ctx context.Context, appID string, appLogWriter, daprdLogWriter io.Writer, podClient v1.PodInterface) error {
var err error
var podList *corev1.PodList
counter := 0
for {
podList, err = getPods(ctx, appID, podClient)
if err != nil {
return fmt.Errorf("error listing the pod with label %s=%s: %w", daprAppIDKey, appID, err)
}
if len(podList.Items) != 0 {
break
}
counter++
if counter == maxListingRetry {
return fmt.Errorf("error getting logs: error listing the pod with label %s=%s after %d retires", daprAppIDKey, appID, maxListingRetry)
}
// Retry after a delay.
time.Sleep(listingDelay)
}
for _, pod := range podList.Items {
print.InfoStatusEvent(os.Stdout, "Streaming logs for containers in pod %q", pod.GetName())
for _, container := range pod.Spec.Containers {
fileWriter := daprdLogWriter
if container.Name != daprdContainerName {
fileWriter = appLogWriter
}
// create a go routine for each container to stream logs into file/console.
go func(pod, containerName, appID string, fileWriter io.Writer) {
loop:
for {
req := podClient.GetLogs(pod, &corev1.PodLogOptions{
Container: containerName,
Follow: true,
})
stream, err := req.Stream(ctx)
if err != nil {
switch {
case strings.Contains(err.Error(), "Pending"):
// Retry after a delay.
time.Sleep(streamingDelay)
continue loop
case strings.Contains(err.Error(), "ContainerCreating"):
// Retry after a delay.
time.Sleep(streamingDelay)
continue loop
case errors.Is(err, context.Canceled):
return
default:
return
}
}
defer stream.Close()
if containerName != daprdContainerName {
streamScanner := bufio.NewScanner(stream)
for streamScanner.Scan() {
fmt.Fprintln(fileWriter, print.Blue(fmt.Sprintf("== APP - %s == %s", appID, streamScanner.Text())))
}
} else {
_, err = io.Copy(fileWriter, stream)
if err != nil {
switch {
case errors.Is(err, context.Canceled):
return
default:
return
}
}
}
return
}
}(pod.GetName(), container.Name, appID, fileWriter)
}
}
return nil
}
func getPods(ctx context.Context, appID string, podClient v1.PodInterface) (*corev1.PodList, error) {
listCtx, cancel := context.WithTimeout(ctx, 30*time.Second)
labelSelector := fmt.Sprintf("%s=%s", daprAppIDKey, appID)
podList, err := podClient.List(listCtx, metav1.ListOptions{
LabelSelector: labelSelector,
})
cancel()
if err != nil {
return nil, err
}
return podList, nil
}

View File

@ -42,7 +42,7 @@ func IsMTLSEnabled() (bool, error) {
if err != nil {
return false, err
}
return c.Spec.MTLSSpec.Enabled, nil
return *c.Spec.MTLSSpec.Enabled, nil
}
func getSystemConfig() (*v1alpha1.Configuration, error) {

View File

@ -15,24 +15,31 @@ package kubernetes
import (
"context"
"errors"
"fmt"
"strings"
core_v1 "k8s.io/api/core/v1"
v1 "k8s.io/apimachinery/pkg/apis/meta/v1"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/labels"
"k8s.io/apimachinery/pkg/watch"
k8s "k8s.io/client-go/kubernetes"
)
func ListPodsInterface(client k8s.Interface, labelSelector map[string]string) (*core_v1.PodList, error) {
opts := v1.ListOptions{}
const podWatchErrTemplate = "error creating pod watcher"
var errPodUnknown error = errors.New("pod in unknown/failed state")
func ListPodsInterface(client k8s.Interface, labelSelector map[string]string) (*corev1.PodList, error) {
opts := metav1.ListOptions{}
if labelSelector != nil {
opts.LabelSelector = labels.FormatLabels(labelSelector)
}
return client.CoreV1().Pods(v1.NamespaceAll).List(context.TODO(), opts)
return client.CoreV1().Pods(metav1.NamespaceAll).List(context.TODO(), opts)
}
func ListPods(client *k8s.Clientset, namespace string, labelSelector map[string]string) (*core_v1.PodList, error) {
opts := v1.ListOptions{}
func ListPods(client *k8s.Clientset, namespace string, labelSelector map[string]string) (*corev1.PodList, error) {
opts := metav1.ListOptions{}
if labelSelector != nil {
opts.LabelSelector = labels.FormatLabels(labelSelector)
}
@ -41,8 +48,8 @@ func ListPods(client *k8s.Clientset, namespace string, labelSelector map[string]
// CheckPodExists returns a boolean representing the pod's existence and the namespace that the given pod resides in,
// or empty if not present in the given namespace.
func CheckPodExists(client *k8s.Clientset, namespace string, labelSelector map[string]string, deployName string) (bool, string) {
opts := v1.ListOptions{}
func CheckPodExists(client k8s.Interface, namespace string, labelSelector map[string]string, deployName string) (bool, string) {
opts := metav1.ListOptions{}
if labelSelector != nil {
opts.LabelSelector = labels.FormatLabels(labelSelector)
}
@ -53,7 +60,7 @@ func CheckPodExists(client *k8s.Clientset, namespace string, labelSelector map[s
}
for _, pod := range podList.Items {
if pod.Status.Phase == core_v1.PodRunning {
if pod.Status.Phase == corev1.PodRunning {
if strings.HasPrefix(pod.Name, deployName) {
return true, pod.Namespace
}
@ -61,3 +68,61 @@ func CheckPodExists(client *k8s.Clientset, namespace string, labelSelector map[s
}
return false, ""
}
func createPodWatcher(ctx context.Context, client k8s.Interface, namespace, appID string) (watch.Interface, error) {
labelSelector := fmt.Sprintf("%s=%s", daprAppIDKey, appID)
opts := metav1.ListOptions{
TypeMeta: metav1.TypeMeta{},
LabelSelector: labelSelector,
}
return client.CoreV1().Pods(namespace).Watch(ctx, opts)
}
func waitPodDeleted(ctx context.Context, client k8s.Interface, namespace, appID string) error {
watcher, err := createPodWatcher(ctx, client, namespace, appID)
if err != nil {
return fmt.Errorf("%s : %w", podWatchErrTemplate, err)
}
defer watcher.Stop()
for {
select {
case event := <-watcher.ResultChan():
if event.Type == watch.Deleted {
return nil
}
case <-ctx.Done():
return fmt.Errorf("error context cancelled while waiting for pod deletion: %w", context.Canceled)
}
}
}
func waitPodRunning(ctx context.Context, client k8s.Interface, namespace, appID string) error {
watcher, err := createPodWatcher(ctx, client, namespace, appID)
if err != nil {
return fmt.Errorf("%s : %w", podWatchErrTemplate, err)
}
defer watcher.Stop()
for {
select {
case event := <-watcher.ResultChan():
pod := event.Object.(*corev1.Pod)
if pod.Status.Phase == corev1.PodRunning {
return nil
} else if pod.Status.Phase == corev1.PodFailed || pod.Status.Phase == corev1.PodUnknown {
return fmt.Errorf("error waiting for pod run: %w", errPodUnknown)
}
case <-ctx.Done():
return fmt.Errorf("error context cancelled while waiting for pod run: %w", context.Canceled)
}
}
}

View File

@ -28,9 +28,9 @@ func TestListPodsInterface(t *testing.T) {
output, err := ListPodsInterface(k8s, map[string]string{
"test": "test",
})
assert.Nil(t, err, "unexpected error")
assert.NoError(t, err, "unexpected error")
assert.NotNil(t, output, "Expected empty list")
assert.Equal(t, 0, len(output.Items), "Expected length 0")
assert.Empty(t, output.Items, "Expected length 0")
})
t.Run("one matching pod", func(t *testing.T) {
k8s := fake.NewSimpleClientset((&v1.Pod{
@ -46,9 +46,9 @@ func TestListPodsInterface(t *testing.T) {
output, err := ListPodsInterface(k8s, map[string]string{
"test": "test",
})
assert.Nil(t, err, "unexpected error")
assert.NoError(t, err, "unexpected error")
assert.NotNil(t, output, "Expected non empty list")
assert.Equal(t, 1, len(output.Items), "Expected length 0")
assert.Len(t, output.Items, 1, "Expected length 0")
assert.Equal(t, "test", output.Items[0].Name, "expected name to match")
assert.Equal(t, "test", output.Items[0].Namespace, "expected namespace to match")
})

View File

@ -14,6 +14,7 @@ limitations under the License.
package kubernetes
import (
"errors"
"fmt"
"io"
"net/http"
@ -133,7 +134,7 @@ func (pf *PortForward) Init() error {
return fmt.Errorf("can not get the local and remote ports: %w", err)
}
if len(ports) == 0 {
return fmt.Errorf("can not get the local and remote ports: error getting ports length")
return errors.New("can not get the local and remote ports: error getting ports length")
}
pf.LocalPort = int(ports[0].Local)

View File

@ -15,6 +15,8 @@ package kubernetes
import (
"crypto/ecdsa"
"crypto/elliptic"
"crypto/rand"
"crypto/x509"
"encoding/pem"
"errors"
@ -26,8 +28,8 @@ import (
"k8s.io/helm/pkg/strvals"
"github.com/dapr/cli/pkg/print"
"github.com/dapr/dapr/pkg/sentry/ca"
"github.com/dapr/dapr/pkg/sentry/certs"
"github.com/dapr/cli/utils"
"github.com/dapr/dapr/pkg/sentry/server/ca"
)
type RenewCertificateParams struct {
@ -37,6 +39,7 @@ type RenewCertificateParams struct {
RootPrivateKeyFilePath string
ValidUntil time.Duration
Timeout uint
ImageVariant string
}
func RenewCertificate(conf RenewCertificateParams) error {
@ -49,7 +52,6 @@ func RenewCertificate(conf RenewCertificateParams) error {
conf.RootCertificateFilePath,
conf.IssuerCertificateFilePath,
conf.IssuerPrivateKeyFilePath)
if err != nil {
return err
}
@ -57,13 +59,12 @@ func RenewCertificate(conf RenewCertificateParams) error {
rootCertBytes, issuerCertBytes, issuerKeyBytes, err = GenerateNewCertificates(
conf.ValidUntil,
conf.RootPrivateKeyFilePath)
if err != nil {
return err
}
}
print.InfoStatusEvent(os.Stdout, "Updating certifcates in your Kubernetes cluster")
err = renewCertificate(rootCertBytes, issuerCertBytes, issuerKeyBytes, conf.Timeout)
err = renewCertificate(rootCertBytes, issuerCertBytes, issuerKeyBytes, conf.Timeout, conf.ImageVariant)
if err != nil {
return err
}
@ -86,29 +87,44 @@ func parseCertificateFiles(rootCert, issuerCert, issuerKey string) ([]byte, []by
return rootCertBytes, issuerCertBytes, issuerKeyBytes, nil
}
func renewCertificate(rootCert, issuerCert, issuerKey []byte, timeout uint) error {
func renewCertificate(rootCert, issuerCert, issuerKey []byte, timeout uint, imageVariant string) error {
var daprVersion, daprImageVariant string
status, err := GetDaprResourcesStatus()
if err != nil {
return err
}
daprVersion := GetDaprVersion(status)
daprVersion = GetDaprVersion(status)
print.InfoStatusEvent(os.Stdout, "Dapr control plane version %s detected in namespace %s", daprVersion, status[0].Namespace)
// Get the control plane version from daprversion(1.x.x-mariner), if image variant is provided.
// Here, imageVariant is used only to extract the actual control plane version,
// and do some validation on top of that.
if imageVariant != "" {
daprVersion, daprImageVariant = utils.GetVersionAndImageVariant(daprVersion)
if daprImageVariant != imageVariant {
return fmt.Errorf("error in parsing dapr version. found image variant %q is not same as provided value %q", daprImageVariant, imageVariant)
}
}
helmConf, err := helmConfig(status[0].Namespace)
if err != nil {
return err
}
daprChart, err := daprChart(daprVersion, helmConf)
helmRepo := utils.GetEnv("DAPR_HELM_REPO_URL", daprHelmRepo)
daprChart, err := getHelmChart(daprVersion, "dapr", helmRepo, helmConf)
if err != nil {
return err
}
upgradeClient := helm.NewUpgrade(helmConf)
// Reuse the existing helm configuration values i.e. tags, registry, etc.
upgradeClient.ReuseValues = true
upgradeClient.Wait = true
upgradeClient.Timeout = time.Duration(timeout) * time.Second
upgradeClient.Timeout = time.Duration(timeout) * time.Second //nolint:gosec
upgradeClient.Namespace = status[0].Namespace
// Override the helm configuration values with the new certificates.
vals, err := createHelmParamsForNewCertificates(string(rootCert), string(issuerCert), string(issuerKey))
if err != nil {
return err
@ -130,12 +146,12 @@ func createHelmParamsForNewCertificates(ca, issuerCert, issuerKey string) (map[s
args := []string{}
if ca != "" && issuerCert != "" && issuerKey != "" {
args = append(args, fmt.Sprintf("dapr_sentry.tls.root.certPEM=%s", ca),
fmt.Sprintf("dapr_sentry.tls.issuer.certPEM=%s", issuerCert),
fmt.Sprintf("dapr_sentry.tls.issuer.keyPEM=%s", issuerKey),
args = append(args, "dapr_sentry.tls.root.certPEM="+ca,
"dapr_sentry.tls.issuer.certPEM="+issuerCert,
"dapr_sentry.tls.issuer.keyPEM="+issuerKey,
)
} else {
return nil, fmt.Errorf("parameters not found")
return nil, errors.New("parameters not found")
}
for _, v := range args {
@ -163,7 +179,7 @@ func GenerateNewCertificates(validUntil time.Duration, privateKeyFile string) ([
}
} else {
var err error
rootKey, err = certs.GenerateECPrivateKey()
rootKey, err = ecdsa.GenerateKey(elliptic.P256(), rand.Reader)
if err != nil {
return nil, nil, nil, err
}
@ -172,13 +188,18 @@ func GenerateNewCertificates(validUntil time.Duration, privateKeyFile string) ([
if err != nil {
return nil, nil, nil, err
}
allowedClockSkew, err := time.ParseDuration(systemConfig.Spec.MTLSSpec.AllowedClockSkew)
var allowedClockSkew time.Duration
if systemConfig.Spec.MTLSSpec.AllowedClockSkew != nil {
allowedClockSkew, err = time.ParseDuration(*systemConfig.Spec.MTLSSpec.AllowedClockSkew)
if err != nil {
return nil, nil, nil, err
}
}
bundle, err := ca.GenerateBundle(rootKey, "cluster.local", allowedClockSkew, &validUntil)
if err != nil {
return nil, nil, nil, err
}
_, rootCertPem, issuerCertPem, issuerKeyPem, err := ca.GetNewSelfSignedCertificates(rootKey, validUntil, allowedClockSkew)
if err != nil {
return nil, nil, nil, err
}
return rootCertPem, issuerCertPem, issuerKeyPem, nil
return bundle.TrustAnchors, bundle.IssChainPEM, bundle.IssKeyPEM, nil
}

View File

@ -13,24 +13,447 @@ limitations under the License.
package kubernetes
// RunConfig represents the application configuration parameters.
type RunConfig struct {
AppID string
AppPort int
HTTPPort int
GRPCPort int
CodeDirectory string
Arguments []string
Image string
import (
"context"
"errors"
"fmt"
"io"
"os"
"path/filepath"
"strings"
"sync"
"syscall"
"time"
appV1 "k8s.io/api/apps/v1"
corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/util/intstr"
k8s "k8s.io/client-go/kubernetes"
podsv1 "k8s.io/client-go/kubernetes/typed/core/v1"
// Specifically use k8s sig yaml to marshal into json, then convert to yaml.
k8sYaml "sigs.k8s.io/yaml"
"github.com/dapr/cli/pkg/print"
"github.com/dapr/cli/pkg/runfileconfig"
daprsyscall "github.com/dapr/cli/pkg/syscall"
"github.com/dapr/cli/utils"
"github.com/dapr/dapr/pkg/client/clientset/versioned"
)
const (
serviceKind = "Service"
deploymentKind = "Deployment"
serviceAPIVersion = "v1"
deploymentAPIVersion = "apps/v1"
loadBalanceType = "LoadBalancer"
daprEnableAnnotationKey = "dapr.io/enabled"
daprConfigAnnotationKey = "dapr.io/config"
daprConfigAnnotationValue = "appconfig"
serviceFileName = "service.yaml"
deploymentFileName = "deployment.yaml"
appLabelKey = "app"
nameKey = "name"
namespaceKey = "namespace"
labelsKey = "labels"
tcpProtocol = "TCP"
podCreationDeletionTimeout = 1 * time.Minute
)
type deploymentConfig struct {
Kind string `json:"kind"`
APIVersion string `json:"apiVersion"`
Metadata map[string]any `json:"metadata"`
Spec appV1.DeploymentSpec `json:"spec"`
}
// RunOutput represents the run output.
type RunOutput struct {
Message string
type serviceConfig struct {
Kind string `json:"kind"`
APIVersion string `json:"apiVersion"`
Metadata map[string]any `json:"metadata"`
Spec corev1.ServiceSpec `json:"spec"`
}
// Run executes the application based on the run configuration.
func Run(config *RunConfig) (*RunOutput, error) {
//nolint
return nil, nil
type runState struct {
serviceFilePath string
deploymentFilePath string
app runfileconfig.App
logCancel context.CancelFunc
}
// Run executes the application based on the run file configuration.
// Run creates a temporary `deploy` folder within the app/.dapr directory and then applies that to the context pointed to
// kubectl client.
func Run(runFilePath string, config runfileconfig.RunFileConfig) (bool, error) {
// At this point, we expect the runfile to be parsed and the values within config
// Validations and default setting will only be done after this point.
var exitWithError bool
// get k8s client for PodsInterface.
client, cErr := Client()
if cErr != nil {
// exit with error.
return true, fmt.Errorf("error getting k8s client: %w", cErr)
}
// get dapr k8s client.
daprClient, cErr := DaprClient()
if cErr != nil {
// exit with error.
return true, fmt.Errorf("error getting dapr k8s client: %w", cErr)
}
namespace := corev1.NamespaceDefault
podsInterface := client.CoreV1().Pods(namespace)
// setup a monitoring context for shutdown call from another cli process.
monitoringContext, monitoringCancel := context.WithCancel(context.Background())
defer monitoringCancel()
// setup shutdown notify channel.
sigCh := make(chan os.Signal, 1)
daprsyscall.SetupShutdownNotify(sigCh)
runStates := []runState{}
print.InfoStatusEvent(os.Stdout, "This is a preview feature and subject to change in future releases.")
for _, app := range config.Apps {
print.StatusEvent(os.Stdout, print.LogInfo, "Validating config and starting app %q", app.RunConfig.AppID)
// Set defaults if zero value provided in config yaml.
app.RunConfig.SetDefaultFromSchema()
// Validate validates the configs for k8s and modifies appId etc.
err := app.RunConfig.ValidateK8s()
if err != nil {
print.FailureStatusEvent(os.Stderr, "Error validating run config for app %q present in %s: %s", app.RunConfig.AppID, runFilePath, err.Error())
exitWithError = true
break
}
var svc serviceConfig
// create default service config.
if app.ContainerConfiguration.CreateService {
svc = createServiceConfig(app)
}
// create default deployment config.
dep := createDeploymentConfig(daprClient, app)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Error creating deployment file for app %q present in %s: %s", app.RunConfig.AppID, runFilePath, err.Error())
exitWithError = true
break
}
// overwrite <app-id>/.dapr/deploy/service.yaml.
// overwrite <app-id>/.dapr/deploy/deployment.yaml.
err = writeYamlFile(app, svc, dep)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Error creating deployment/service yaml files: %s", err.Error())
exitWithError = true
break
}
deployDir := app.GetDeployDir()
print.InfoStatusEvent(os.Stdout, "Deploying app %q to Kubernetes", app.AppID)
serviceFilePath := filepath.Join(deployDir, serviceFileName)
deploymentFilePath := filepath.Join(deployDir, deploymentFileName)
rState := runState{}
if app.CreateService {
print.InfoStatusEvent(os.Stdout, "Deploying service YAML %q to Kubernetes", serviceFilePath)
err = deployYamlToK8s(serviceFilePath)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Error deploying service yaml file %q : %s", serviceFilePath, err.Error())
exitWithError = true
break
}
rState.serviceFilePath = serviceFilePath
}
print.InfoStatusEvent(os.Stdout, "Deploying deployment YAML %q to Kubernetes", deploymentFilePath)
err = deployYamlToK8s(deploymentFilePath)
if err != nil {
print.FailureStatusEvent(os.Stderr, "Error deploying deployment yaml file %q : %s", deploymentFilePath, err.Error())
exitWithError = true
break
}
// create log files and save state.
err = app.CreateDaprdLogFile()
if err != nil {
print.StatusEvent(os.Stderr, print.LogFailure, "Error getting daprd log file for app %q present in %s: %s", app.AppID, runFilePath, err.Error())
exitWithError = true
break
}
err = app.CreateAppLogFile()
if err != nil {
print.StatusEvent(os.Stderr, print.LogFailure, "Error getting app log file for app %q present in %s: %s", app.AppID, runFilePath, err.Error())
exitWithError = true
break
}
daprdLogWriter := runfileconfig.GetLogWriter(app.DaprdLogWriteCloser, app.DaprdLogDestination)
// appDaprdWriter := runExec.GetAppDaprdWriter(app, false).
appLogWriter := runfileconfig.GetLogWriter(app.AppLogWriteCloser, app.AppLogDestination)
customAppLogWriter := print.CustomLogWriter{W: appLogWriter}
ctx, cancel := context.WithTimeout(context.Background(), podCreationDeletionTimeout)
err = waitPodRunning(ctx, client, namespace, app.AppID)
cancel()
if err != nil {
print.WarningStatusEvent(os.Stderr, "Error deploying pod to Kubernetes. See logs directly from Kubernetes command line.")
// Close the log files since there is deployment error, and the container might be in crash loop back off state.
app.CloseAppLogFile()
app.CloseDaprdLogFile()
} else {
logContext, cancel := context.WithCancel(context.Background())
rState.logCancel = cancel
err = setupLogs(logContext, app.AppID, daprdLogWriter, customAppLogWriter, podsInterface)
if err != nil {
print.StatusEvent(os.Stderr, print.LogWarning, "Error setting up logs for app %q present in %q . See logs directly from Kubernetes command line.: %s ", app.AppID, runFilePath, err.Error())
}
}
rState.deploymentFilePath = deploymentFilePath
rState.app = app
// append runSate only on successful k8s deploy.
runStates = append(runStates, rState)
print.InfoStatusEvent(os.Stdout, "Writing log files to directory : %s", app.GetLogsDir())
}
// If all apps have been started and there are no errors in starting the apps wait for signal from sigCh.
if !exitWithError {
print.InfoStatusEvent(os.Stdout, "Starting to monitor Kubernetes pods for deletion.")
go monitorK8sPods(monitoringContext, client, namespace, runStates, sigCh)
// After all apps started wait for sigCh.
<-sigCh
monitoringCancel()
print.InfoStatusEvent(os.Stdout, "Stopping Kubernetes pods monitoring.")
// To add a new line in Stdout.
fmt.Println()
print.InfoStatusEvent(os.Stdout, "Received signal to stop. Deleting K8s Dapr app deployments.")
}
closeErr := gracefullyShutdownK8sDeployment(runStates, client, namespace)
return exitWithError, closeErr
}
func createServiceConfig(app runfileconfig.App) serviceConfig {
return serviceConfig{
Kind: serviceKind,
APIVersion: serviceAPIVersion,
Metadata: map[string]any{
nameKey: app.RunConfig.AppID,
labelsKey: map[string]string{
appLabelKey: app.AppID,
},
},
Spec: corev1.ServiceSpec{
Ports: []corev1.ServicePort{
{
Protocol: tcpProtocol,
Port: 80,
TargetPort: intstr.FromInt(app.AppPort),
},
},
Selector: map[string]string{
appLabelKey: app.AppID,
},
Type: loadBalanceType,
},
}
}
func createDeploymentConfig(client versioned.Interface, app runfileconfig.App) deploymentConfig {
replicas := int32(1)
dep := deploymentConfig{
Kind: deploymentKind,
APIVersion: deploymentAPIVersion,
Metadata: map[string]any{
nameKey: app.AppID,
namespaceKey: corev1.NamespaceDefault,
},
}
dep.Spec = appV1.DeploymentSpec{
Replicas: &replicas,
Selector: &metav1.LabelSelector{
MatchLabels: map[string]string{
appLabelKey: app.AppID,
},
},
Template: corev1.PodTemplateSpec{
ObjectMeta: metav1.ObjectMeta{
Labels: map[string]string{
appLabelKey: app.AppID,
},
Annotations: app.RunConfig.GetAnnotations(),
},
Spec: corev1.PodSpec{
Containers: []corev1.Container{
{
Name: app.AppID,
Image: app.ContainerImage,
Env: getEnv(app),
ImagePullPolicy: corev1.PullPolicy(app.ContainerImagePullPolicy),
},
},
},
},
}
// Set dapr.io/enable annotation.
dep.Spec.Template.ObjectMeta.Annotations[daprEnableAnnotationKey] = "true"
if ok, _ := isConfigurationPresent(client, corev1.NamespaceDefault, daprConfigAnnotationValue); ok {
// Set dapr.io/config annotation only if present.
dep.Spec.Template.ObjectMeta.Annotations[daprConfigAnnotationKey] = daprConfigAnnotationValue
} else {
print.WarningStatusEvent(os.Stderr, "Dapr configuration %q not found in namespace %q. Skipping annotation %q", daprConfigAnnotationValue, corev1.NamespaceDefault, daprConfigAnnotationKey)
}
// set containerPort only if app port is present.
if app.AppPort != 0 {
dep.Spec.Template.Spec.Containers[0].Ports = []corev1.ContainerPort{
{
ContainerPort: int32(app.AppPort), //nolint:gosec
},
}
}
return dep
}
func getEnv(app runfileconfig.App) []corev1.EnvVar {
envs := app.GetEnv()
envVars := make([]corev1.EnvVar, len(envs))
i := 0
for k, v := range app.GetEnv() {
envVars[i] = corev1.EnvVar{
Name: k,
Value: v,
}
i++
}
return envVars
}
func writeYamlFile(app runfileconfig.App, svc serviceConfig, dep deploymentConfig) error {
var yamlBytes []byte
var err error
var writeFile io.WriteCloser
deployDir := app.GetDeployDir()
if app.CreateService {
yamlBytes, err = k8sYaml.Marshal(svc)
if err != nil {
return fmt.Errorf("error marshalling service yaml: %w", err)
}
serviceFilePath := filepath.Join(deployDir, serviceFileName)
writeFile, err = os.Create(serviceFilePath)
if err != nil {
return fmt.Errorf("error creating file %s : %w", serviceFilePath, err)
}
_, err = writeFile.Write(yamlBytes)
if err != nil {
writeFile.Close()
return fmt.Errorf("error writing to file %s : %w", serviceFilePath, err)
}
writeFile.Close()
}
yamlBytes, err = k8sYaml.Marshal(dep)
if err != nil {
return fmt.Errorf("error marshalling deployment yaml: %w", err)
}
deploymentFilePath := filepath.Join(deployDir, deploymentFileName)
writeFile, err = os.Create(deploymentFilePath)
if err != nil {
return fmt.Errorf("error creating file %s : %w", deploymentFilePath, err)
}
_, err = writeFile.Write(yamlBytes)
if err != nil {
writeFile.Close()
return fmt.Errorf("error writing to file %s : %w", deploymentFilePath, err)
}
writeFile.Close()
return nil
}
func deployYamlToK8s(yamlToDeployPath string) error {
_, err := os.Stat(yamlToDeployPath)
if os.IsNotExist(err) {
return fmt.Errorf("error given file %q does not exist", yamlToDeployPath)
}
_, err = utils.RunCmdAndWait("kubectl", "apply", "-f", yamlToDeployPath)
if err != nil {
return fmt.Errorf("error deploying the yaml %s to Kubernetes: %w", yamlToDeployPath, err)
}
return nil
}
func deleteYamlK8s(yamlToDeletePath string) error {
print.InfoStatusEvent(os.Stdout, "Deleting %q from Kubernetes", yamlToDeletePath)
_, err := os.Stat(yamlToDeletePath)
if os.IsNotExist(err) {
return fmt.Errorf("error given file %q does not exist", yamlToDeletePath)
}
_, err = utils.RunCmdAndWait("kubectl", "delete", "-f", yamlToDeletePath)
if err != nil {
return fmt.Errorf("error deleting the yaml %s from Kubernetes: %w", yamlToDeletePath, err)
}
return nil
}
func setupLogs(ctx context.Context, appID string, daprdLogWriter, appLogWriter io.Writer, podInterface podsv1.PodInterface) error {
return streamContainerLogsToDisk(ctx, appID, appLogWriter, daprdLogWriter, podInterface)
}
func gracefullyShutdownK8sDeployment(runStates []runState, client k8s.Interface, namespace string) error {
errs := make([]error, 0, len(runStates)*4)
for _, r := range runStates {
if len(r.serviceFilePath) != 0 {
errs = append(errs, deleteYamlK8s(r.serviceFilePath))
}
errs = append(errs, deleteYamlK8s(r.deploymentFilePath))
labelSelector := map[string]string{
daprAppIDKey: r.app.AppID,
}
if ok, _ := CheckPodExists(client, namespace, labelSelector, r.app.AppID); ok {
ctx, cancel := context.WithTimeout(context.Background(), podCreationDeletionTimeout)
err := waitPodDeleted(ctx, client, namespace, r.app.AppID)
cancel()
if err != nil {
// swallowing err here intentionally.
print.WarningStatusEvent(os.Stderr, "Error waiting for pods to be deleted. Final logs might only be partially available.")
}
}
// shutdown logs.
if r.logCancel != nil { // checking nil, in scenarios where deployments are not run correctly.
r.logCancel()
}
errs = append(errs, r.app.CloseAppLogFile(), r.app.CloseDaprdLogFile())
}
return errors.Join(errs...)
}
func monitorK8sPods(ctx context.Context, client k8s.Interface, namespace string, runStates []runState, sigCh chan os.Signal) {
// for each app wait for pod to be deleted, if all pods are deleted, then send shutdown signal to the cli process.
wg := sync.WaitGroup{}
for _, r := range runStates {
wg.Add(1)
go func(appID string, wg *sync.WaitGroup) {
err := waitPodDeleted(ctx, client, namespace, appID)
if err != nil && strings.Contains(err.Error(), podWatchErrTemplate) {
print.WarningStatusEvent(os.Stderr, "Error monitoring Kubernetes pod(s) for app %q.", appID)
}
wg.Done()
}(r.app.AppID, &wg)
}
wg.Wait()
// Send signal to gracefully close log writers and shut down process.
sigCh <- syscall.SIGINT
}

View File

@ -33,6 +33,7 @@ var controlPlaneLabels = []string{
"dapr-placement-server",
"dapr-sidecar-injector",
"dapr-dashboard",
"dapr-scheduler-server",
}
type StatusClient struct {
@ -64,7 +65,6 @@ func NewStatusClient() (*StatusClient, error) {
// List status for Dapr resources.
func (s *StatusClient) Status() ([]StatusOutput, error) {
//nolint
client := s.client
if client == nil {
return nil, errors.New("kubernetes client not initialized")
@ -96,7 +96,11 @@ func (s *StatusClient) Status() ([]StatusOutput, error) {
namespace := pod.GetNamespace()
age := age.GetAge(pod.CreationTimestamp.Time)
created := pod.CreationTimestamp.Format("2006-01-02 15:04.05")
version := image[strings.IndexAny(image, ":")+1:]
// Version is part of the docker image tag which is expected to be present at the end of image uri.
// expected format: <image>:<tag>. For example: daprio/dapr:1.8.0.
// tag can be either <version> or <version>-<image-variant>. For example: 1.8.0-mariner.
version := image[strings.LastIndex(image, ":")+1:]
status := ""
// loop through all replicas and update to Running/Healthy status only if all instances are Running and Healthy.

View File

@ -25,37 +25,51 @@ import (
"k8s.io/client-go/kubernetes/fake"
)
const (
daprImageTag = "daprio/dapr:0.0.1"
daprDashboardImageTag = "daprio/dashboard:0.0.1"
)
type podDetails struct {
name string
appName string
createdAt time.Time
state v1.ContainerState
ready bool
imageURI string
}
func newTestSimpleK8s(objects ...runtime.Object) *StatusClient {
client := StatusClient{}
client.client = fake.NewSimpleClientset(objects...)
return &client
}
func newDaprControlPlanePod(name string, appName string, creationTime time.Time, state v1.ContainerState, ready bool) *v1.Pod {
func newDaprControlPlanePod(pd podDetails) *v1.Pod {
return &v1.Pod{
ObjectMeta: metav1.ObjectMeta{
Name: name,
Name: pd.name,
Namespace: "dapr-system",
Annotations: map[string]string{},
Labels: map[string]string{
"app": appName,
"app": pd.appName,
},
CreationTimestamp: metav1.Time{
Time: creationTime,
Time: pd.createdAt,
},
},
Status: v1.PodStatus{
ContainerStatuses: []v1.ContainerStatus{
{
State: state,
Ready: ready,
State: pd.state,
Ready: pd.ready,
},
},
},
Spec: v1.PodSpec{
Containers: []v1.Container{
{
Image: name + ":0.0.1",
Image: pd.imageURI,
},
},
},
@ -69,22 +83,27 @@ func TestStatus(t *testing.T) {
if err != nil {
t.Fatalf("%s status should not raise an error", err.Error())
}
assert.Equal(t, 0, len(status), "Expected status to be empty list")
assert.Empty(t, status, "Expected status to be empty list")
})
t.Run("one status waiting", func(t *testing.T) {
k8s := newTestSimpleK8s(newDaprControlPlanePod(
"dapr-dashboard-58877dbc9d-n8qg2", "dapr-dashboard",
time.Now(),
v1.ContainerState{
pd := podDetails{
name: "dapr-dashboard-58877dbc9d-n8qg2",
appName: "dapr-dashboard",
createdAt: time.Now(),
state: v1.ContainerState{
Waiting: &v1.ContainerStateWaiting{
Reason: "test",
Message: "test",
},
}, false))
},
ready: false,
imageURI: "daprio/dapr-dashboard:0.0.1",
}
k8s := newTestSimpleK8s(newDaprControlPlanePod(pd))
status, err := k8s.Status()
assert.Nil(t, err, "status should not raise an error")
assert.Equal(t, 1, len(status), "Expected status to be non-empty list")
assert.NoError(t, err, "status should not raise an error")
assert.Len(t, status, 1, "Expected status to be non-empty list")
stat := status[0]
assert.Equal(t, "dapr-dashboard", stat.Name, "expected name to match")
assert.Equal(t, "dapr-system", stat.Namespace, "expected namespace to match")
@ -96,19 +115,24 @@ func TestStatus(t *testing.T) {
t.Run("one status running", func(t *testing.T) {
testTime := time.Now()
k8s := newTestSimpleK8s(newDaprControlPlanePod(
"dapr-dashboard-58877dbc9d-n8qg2", "dapr-dashboard",
testTime.Add(time.Duration(-20)*time.Minute),
v1.ContainerState{
pd := podDetails{
name: "dapr-dashboard-58877dbc9d-n8qg2",
appName: "dapr-dashboard",
createdAt: testTime.Add(time.Duration(-20) * time.Minute),
state: v1.ContainerState{
Running: &v1.ContainerStateRunning{
StartedAt: metav1.Time{
Time: testTime.Add(time.Duration(-19) * time.Minute),
},
},
}, true))
},
ready: true,
imageURI: "daprio/dapr-dashboard:0.0.1",
}
k8s := newTestSimpleK8s(newDaprControlPlanePod(pd))
status, err := k8s.Status()
assert.Nil(t, err, "status should not raise an error")
assert.Equal(t, 1, len(status), "Expected status to be non-empty list")
assert.NoError(t, err, "status should not raise an error")
assert.Len(t, status, 1, "Expected status to be non-empty list")
stat := status[0]
assert.Equal(t, "dapr-dashboard", stat.Name, "expected name to match")
assert.Equal(t, "dapr-system", stat.Namespace, "expected namespace to match")
@ -116,24 +140,28 @@ func TestStatus(t *testing.T) {
assert.Equal(t, "0.0.1", stat.Version, "expected version to match")
assert.Equal(t, 1, stat.Replicas, "expected replicas to match")
assert.Equal(t, "True", stat.Healthy, "expected health to match")
assert.Equal(t, stat.Status, "Running", "expected running status")
assert.Equal(t, "Running", stat.Status, "expected running status")
})
t.Run("one status terminated", func(t *testing.T) {
testTime := time.Now()
k8s := newTestSimpleK8s(newDaprControlPlanePod(
"dapr-dashboard-58877dbc9d-n8qg2", "dapr-dashboard",
testTime.Add(time.Duration(-20)*time.Minute),
v1.ContainerState{
pd := podDetails{
name: "dapr-dashboard-58877dbc9d-n8qg2",
appName: "dapr-dashboard",
createdAt: testTime.Add(time.Duration(-20) * time.Minute),
state: v1.ContainerState{
Terminated: &v1.ContainerStateTerminated{
ExitCode: 1,
},
}, false))
},
ready: false,
imageURI: "daprio/dapr-dashboard:0.0.1",
}
k8s := newTestSimpleK8s(newDaprControlPlanePod(pd))
status, err := k8s.Status()
assert.Nil(t, err, "status should not raise an error")
assert.Equal(t, 1, len(status), "Expected status to be non-empty list")
assert.NoError(t, err, "status should not raise an error")
assert.Len(t, status, 1, "Expected status to be non-empty list")
stat := status[0]
assert.Equal(t, "dapr-dashboard", stat.Name, "expected name to match")
assert.Equal(t, "dapr-system", stat.Namespace, "expected namespace to match")
@ -141,28 +169,32 @@ func TestStatus(t *testing.T) {
assert.Equal(t, "0.0.1", stat.Version, "expected version to match")
assert.Equal(t, 1, stat.Replicas, "expected replicas to match")
assert.Equal(t, "False", stat.Healthy, "expected health to match")
assert.Equal(t, stat.Status, "Terminated", "expected terminated status")
assert.Equal(t, "Terminated", stat.Status, "expected terminated status")
})
t.Run("one status pending", func(t *testing.T) {
testTime := time.Now()
pod := newDaprControlPlanePod(
"dapr-dashboard-58877dbc9d-n8qg2", "dapr-dashboard",
testTime.Add(time.Duration(-20)*time.Minute),
v1.ContainerState{
pd := podDetails{
name: "dapr-dashboard-58877dbc9d-n8qg2",
appName: "dapr-dashboard",
createdAt: testTime.Add(time.Duration(-20) * time.Minute),
state: v1.ContainerState{
Terminated: &v1.ContainerStateTerminated{
ExitCode: 1,
},
}, false)
},
ready: false,
imageURI: "daprio/dapr-dashboard:0.0.1",
}
pod := newDaprControlPlanePod(pd)
// delete pod's podstatus.
pod.Status.ContainerStatuses = nil
pod.Status.Phase = v1.PodPending
k8s := newTestSimpleK8s(pod)
status, err := k8s.Status()
assert.Nil(t, err, "status should not raise an error")
assert.Equal(t, 1, len(status), "Expected status to be non-empty list")
assert.NoError(t, err, "status should not raise an error")
assert.Len(t, status, 1, "Expected status to be non-empty list")
stat := status[0]
assert.Equal(t, "dapr-dashboard", stat.Name, "expected name to match")
assert.Equal(t, "dapr-system", stat.Namespace, "expected namespace to match")
@ -170,13 +202,13 @@ func TestStatus(t *testing.T) {
assert.Equal(t, "0.0.1", stat.Version, "expected version to match")
assert.Equal(t, 1, stat.Replicas, "expected replicas to match")
assert.Equal(t, "False", stat.Healthy, "expected health to match")
assert.Equal(t, stat.Status, "Pending", "expected pending status")
assert.Equal(t, "Pending", stat.Status, "expected pending status")
})
t.Run("one status empty client", func(t *testing.T) {
k8s := &StatusClient{}
status, err := k8s.Status()
assert.NotNil(t, err, "status should raise an error")
assert.Error(t, err, "status should raise an error")
assert.Equal(t, "kubernetes client not initialized", err.Error(), "expected errors to match")
assert.Nil(t, status, "expected nil for status")
})
@ -184,22 +216,26 @@ func TestStatus(t *testing.T) {
func TestControlPlaneServices(t *testing.T) {
controlPlaneServices := []struct {
name string
appName string
name string
appName string
imageURI string
}{
{"dapr-dashboard-58877dbc9d-n8qg2", "dapr-dashboard"},
{"dapr-operator-67d7d7bb6c-7h96c", "dapr-operator"},
{"dapr-operator-67d7d7bb6c-2h96d", "dapr-operator"},
{"dapr-operator-67d7d7bb6c-3h96c", "dapr-operator"},
{"dapr-placement-server-0", "dapr-placement-server"},
{"dapr-placement-server-1", "dapr-placement-server"},
{"dapr-placement-server-2", "dapr-placement-server"},
{"dapr-sentry-647759cd46-9ptks", "dapr-sentry"},
{"dapr-sentry-647759cd46-aptks", "dapr-sentry"},
{"dapr-sentry-647759cd46-bptks", "dapr-sentry"},
{"dapr-sidecar-injector-74648c9dcb-5bsmn", "dapr-sidecar-injector"},
{"dapr-sidecar-injector-74648c9dcb-6bsmn", "dapr-sidecar-injector"},
{"dapr-sidecar-injector-74648c9dcb-7bsmn", "dapr-sidecar-injector"},
{"dapr-dashboard-58877dbc9d-n8qg2", "dapr-dashboard", daprDashboardImageTag},
{"dapr-operator-67d7d7bb6c-7h96c", "dapr-operator", daprImageTag},
{"dapr-operator-67d7d7bb6c-2h96d", "dapr-operator", daprImageTag},
{"dapr-operator-67d7d7bb6c-3h96c", "dapr-operator", daprImageTag},
{"dapr-placement-server-0", "dapr-placement-server", daprImageTag},
{"dapr-placement-server-1", "dapr-placement-server", daprImageTag},
{"dapr-placement-server-2", "dapr-placement-server", daprImageTag},
{"dapr-sentry-647759cd46-9ptks", "dapr-sentry", daprImageTag},
{"dapr-sentry-647759cd46-aptks", "dapr-sentry", daprImageTag},
{"dapr-sentry-647759cd46-bptks", "dapr-sentry", daprImageTag},
{"dapr-sidecar-injector-74648c9dcb-5bsmn", "dapr-sidecar-injector", daprImageTag},
{"dapr-sidecar-injector-74648c9dcb-6bsmn", "dapr-sidecar-injector", daprImageTag},
{"dapr-sidecar-injector-74648c9dcb-7bsmn", "dapr-sidecar-injector", daprImageTag},
{"dapr-scheduler-server-0", "dapr-scheduler-server", daprImageTag},
{"dapr-scheduler-server-1", "dapr-scheduler-server", daprImageTag},
{"dapr-scheduler-server-2", "dapr-scheduler-server", daprImageTag},
}
expectedReplicas := map[string]int{}
@ -207,22 +243,27 @@ func TestControlPlaneServices(t *testing.T) {
runtimeObj := make([]runtime.Object, len(controlPlaneServices))
for i, s := range controlPlaneServices {
testTime := time.Now()
runtimeObj[i] = newDaprControlPlanePod(
s.name, s.appName,
testTime.Add(time.Duration(-20)*time.Minute),
v1.ContainerState{
pd := podDetails{
name: s.name,
appName: s.appName,
createdAt: testTime.Add(time.Duration(-20) * time.Minute),
state: v1.ContainerState{
Running: &v1.ContainerStateRunning{
StartedAt: metav1.Time{
Time: testTime.Add(time.Duration(-19) * time.Minute),
},
},
}, true)
},
ready: true,
imageURI: s.imageURI,
}
runtimeObj[i] = newDaprControlPlanePod(pd)
expectedReplicas[s.appName]++
}
k8s := newTestSimpleK8s(runtimeObj...)
status, err := k8s.Status()
assert.Nil(t, err, "status should not raise an error")
assert.NoError(t, err, "status should not raise an error")
assert.Equal(t, len(expectedReplicas), len(status), "Expected status to be empty list")
@ -232,3 +273,41 @@ func TestControlPlaneServices(t *testing.T) {
assert.Equal(t, replicas, stat.Replicas, "expected replicas to match")
}
}
func TestControlPlaneVersion(t *testing.T) {
pd := podDetails{
name: "dapr-sentry-647759cd46-9ptks",
appName: "dapr-sentry",
createdAt: time.Now().Add(time.Duration(-20) * time.Minute),
state: v1.ContainerState{
Running: &v1.ContainerStateRunning{
StartedAt: metav1.Time{
Time: time.Now().Add(time.Duration(-19) * time.Minute),
},
},
},
ready: true,
}
testcases := []struct {
imageURI string
expectedVersion string
}{
{
imageURI: "mockImgReg:0.0.1",
expectedVersion: "0.0.1",
},
{
imageURI: "mockImgRegHost:mockPort:0.0.2",
expectedVersion: "0.0.2",
},
}
for _, tc := range testcases {
pd.imageURI = tc.imageURI
k8s := newTestSimpleK8s(newDaprControlPlanePod(pd))
status, err := k8s.Status()
assert.NoError(t, err, "status should not raise an error")
assert.Len(t, status, 1, "Expected status to be non-empty list")
stat := status[0]
assert.Equal(t, tc.expectedVersion, stat.Version, "expected version to match")
}
}

67
pkg/kubernetes/stop.go Normal file
View File

@ -0,0 +1,67 @@
/*
Copyright 2023 The Dapr Authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package kubernetes
import (
"context"
"errors"
"fmt"
"os"
"path/filepath"
corev1 "k8s.io/api/core/v1"
"github.com/dapr/cli/pkg/print"
"github.com/dapr/cli/pkg/runfileconfig"
)
func Stop(runFilePath string, config runfileconfig.RunFileConfig) error {
errs := []error{}
// get k8s client.
client, cErr := Client()
if cErr != nil {
return fmt.Errorf("error getting k8s client for monitoring pod deletion: %w", cErr)
}
var err error
namespace := corev1.NamespaceDefault
for _, app := range config.Apps {
appError := false
deployDir := app.GetDeployDir()
serviceFilePath := filepath.Join(deployDir, serviceFileName)
deploymentFilePath := filepath.Join(deployDir, deploymentFileName)
if app.CreateService {
err = deleteYamlK8s(serviceFilePath)
if err != nil {
appError = true
}
errs = append(errs, err)
}
err = deleteYamlK8s(deploymentFilePath)
if err != nil {
appError = true
}
errs = append(errs, err)
if !appError {
ctx, cancel := context.WithTimeout(context.Background(), podCreationDeletionTimeout)
// Ignoring errors here as it will anyway be printed in the other dapr cli process.
waitPodDeleted(ctx, client, namespace, app.AppID)
cancel()
} else {
print.WarningStatusEvent(os.Stderr, "Error stopping deployment for app %q in file %q", app.AppID, runFilePath)
}
}
return errors.Join(errs...)
}

View File

@ -24,13 +24,13 @@ import (
)
// Uninstall removes Dapr from a Kubernetes cluster.
func Uninstall(namespace string, uninstallAll bool, timeout uint) error {
func Uninstall(namespace string, uninstallAll bool, uninstallDev bool, timeout uint) error {
config, err := helmConfig(namespace)
if err != nil {
return err
}
exists, err := confirmExist(config)
exists, err := confirmExist(config, daprReleaseName)
if err != nil {
return err
}
@ -41,9 +41,19 @@ func Uninstall(namespace string, uninstallAll bool, timeout uint) error {
}
uninstallClient := helm.NewUninstall(config)
uninstallClient.Timeout = time.Duration(timeout) * time.Second
_, err = uninstallClient.Run(daprReleaseName)
uninstallClient.Timeout = time.Duration(timeout) * time.Second //nolint:gosec
// Uninstall Dashboard as a best effort.
// Chart versions < 1.11 for Dapr will delete dashboard as part of the main chart.
// Deleting Dashboard here is for versions >= 1.11.
uninstallClient.Run(dashboardReleaseName)
if uninstallDev {
// uninstall dapr-dev-zipkin and dapr-dev-redis as best effort.
uninstallThirdParty()
}
_, err = uninstallClient.Run(daprReleaseName)
if err != nil {
return err
}
@ -59,3 +69,14 @@ func Uninstall(namespace string, uninstallAll bool, timeout uint) error {
return nil
}
func uninstallThirdParty() {
print.InfoStatusEvent(os.Stdout, "Removing dapr-dev-redis and dapr-dev-zipkin from the cluster...")
// Uninstall dapr-dev-redis and dapr-dev-zipkin from k8s as best effort.
config, _ := helmConfig(thirdPartyDevNamespace)
uninstallClient := helm.NewUninstall(config)
uninstallClient.Run(redisReleaseName)
uninstallClient.Run(zipkinReleaseName)
}

View File

@ -14,14 +14,22 @@ limitations under the License.
package kubernetes
import (
"context"
"errors"
"fmt"
"net/http"
"os"
"strings"
"time"
helm "helm.sh/helm/v3/pkg/action"
"helm.sh/helm/v3/pkg/chart"
"helm.sh/helm/v3/pkg/release"
core_v1 "k8s.io/api/core/v1"
meta_v1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/helm/pkg/strvals"
"github.com/Masterminds/semver/v3"
"github.com/hashicorp/go-version"
"github.com/dapr/cli/pkg/print"
@ -35,6 +43,7 @@ var crds = []string{
"configuration",
"subscription",
"resiliency",
"httpendpoints",
}
var crdsFullResources = []string{
@ -42,17 +51,32 @@ var crdsFullResources = []string{
"configurations.dapr.io",
"subscriptions.dapr.io",
"resiliencies.dapr.io",
"httpendpoints.dapr.io",
}
var versionWithHAScheduler = semver.MustParse("1.15.0-rc.1")
type UpgradeConfig struct {
RuntimeVersion string
DashboardVersion string
Args []string
Timeout uint
ImageRegistryURI string
ImageVariant string
}
// UpgradeOptions represents options for the upgrade function.
type UpgradeOptions struct {
WithRetry bool
MaxRetries int
RetryInterval time.Duration
}
// UpgradeOption is a functional option type for configuring upgrade.
type UpgradeOption func(*UpgradeOptions)
func Upgrade(conf UpgradeConfig) error {
helmRepo := utils.GetEnv("DAPR_HELM_REPO_URL", daprHelmRepo)
status, err := GetDaprResourcesStatus()
if err != nil {
return err
@ -61,22 +85,55 @@ func Upgrade(conf UpgradeConfig) error {
daprVersion := GetDaprVersion(status)
print.InfoStatusEvent(os.Stdout, "Dapr control plane version %s detected in namespace %s", daprVersion, status[0].Namespace)
helmConf, err := helmConfig(status[0].Namespace)
hasDashboardInDaprChart, err := IsDashboardIncluded(daprVersion)
if err != nil {
return err
}
daprChart, err := daprChart(conf.RuntimeVersion, helmConf)
upgradeClient, helmConf, err := newUpgradeClient(status[0].Namespace, conf)
if err != nil {
return fmt.Errorf("unable to create helm client: %w", err)
}
controlPlaneChart, err := getHelmChart(conf.RuntimeVersion, "dapr", helmRepo, helmConf)
if err != nil {
return fmt.Errorf("unable to get helm chart: %w", err)
}
willHaveDashboardInDaprChart, err := IsDashboardIncluded(conf.RuntimeVersion)
if err != nil {
return err
}
upgradeClient := helm.NewUpgrade(helmConf)
upgradeClient.ResetValues = true
upgradeClient.Namespace = status[0].Namespace
upgradeClient.CleanupOnFail = true
upgradeClient.Wait = true
upgradeClient.Timeout = time.Duration(conf.Timeout) * time.Second
// Before we do anything, checks if installing dashboard is allowed.
if willHaveDashboardInDaprChart && conf.DashboardVersion != "" {
// We cannot install Dashboard separately if Dapr's chart has it already.
return fmt.Errorf("cannot install Dashboard because Dapr version %s already contains it - installation aborted", conf.RuntimeVersion)
}
dashboardExists, err := confirmExist(helmConf, dashboardReleaseName)
if err != nil {
return err
}
if !hasDashboardInDaprChart && willHaveDashboardInDaprChart && dashboardExists {
print.InfoStatusEvent(os.Stdout, "Dashboard being uninstalled prior to Dapr control plane upgrade...")
uninstallClient := helm.NewUninstall(helmConf)
uninstallClient.Timeout = time.Duration(conf.Timeout) * time.Second //nolint:gosec
_, err = uninstallClient.Run(dashboardReleaseName)
if err != nil {
return err
}
}
var dashboardChart *chart.Chart
if conf.DashboardVersion != "" {
dashboardChart, err = getHelmChart(conf.DashboardVersion, dashboardReleaseName, helmRepo, helmConf)
if err != nil {
return err
}
}
print.InfoStatusEvent(os.Stdout, "Starting upgrade...")
@ -107,13 +164,42 @@ func Upgrade(conf UpgradeConfig) error {
return err
}
// used to signal the deletion of the scheduler pods only when downgrading from 1.15 to previous versions to handle incompatible changes
// in other cases the channel should be nil
var downgradeDeletionChan chan error
if !isDowngrade(conf.RuntimeVersion, daprVersion) {
err = applyCRDs(fmt.Sprintf("v%s", conf.RuntimeVersion))
err = applyCRDs("v" + conf.RuntimeVersion)
if err != nil {
return err
return fmt.Errorf("unable to apply CRDs: %w", err)
}
} else {
print.InfoStatusEvent(os.Stdout, "Downgrade detected, skipping CRDs.")
targetVersion, errVersion := semver.NewVersion(conf.RuntimeVersion)
if errVersion != nil {
return fmt.Errorf("unable to parse dapr target version: %w", errVersion)
}
currentVersion, errVersion := semver.NewVersion(daprVersion)
if errVersion != nil {
return fmt.Errorf("unable to parse dapr current version: %w", errVersion)
}
if currentVersion.GreaterThanEqual(versionWithHAScheduler) && targetVersion.LessThan(versionWithHAScheduler) {
downgradeDeletionChan = make(chan error)
// Must delete all scheduler pods from cluster due to incompatible changes in version 1.15 with older versions.
go func() {
// Add an artificial delay to allow helm upgrade to progress and delete the pods only when necessary.
time.Sleep(15 * time.Second)
errDeletion := deleteSchedulerPods(status[0].Namespace, currentVersion, targetVersion)
if errDeletion != nil {
downgradeDeletionChan <- fmt.Errorf("failed to delete scheduler pods: %w", errDeletion)
print.FailureStatusEvent(os.Stderr, "Failed to delete scheduler pods: "+errDeletion.Error())
}
close(downgradeDeletionChan)
}()
}
}
chart, err := GetDaprHelmChartName(helmConf)
@ -121,17 +207,172 @@ func Upgrade(conf UpgradeConfig) error {
return err
}
if _, err = upgradeClient.Run(chart, daprChart, vals); err != nil {
// Deal with known race condition when applying both CRD and CR close together. The Helm upgrade fails
// when a CR is applied tries to be applied before the CRD is fully registered. On each retry we need a
// fresh client since the kube client locally caches the last OpenAPI schema it received from the server.
// See https://github.com/kubernetes/kubectl/issues/1179
_, err = helmUpgrade(upgradeClient, chart, controlPlaneChart, vals, WithRetry(5, 100*time.Millisecond))
if err != nil {
return fmt.Errorf("failure while running upgrade: %w", err)
}
// wait for the deletion of the scheduler pods to finish
if downgradeDeletionChan != nil {
select {
case <-downgradeDeletionChan:
case <-time.After(3 * time.Minute):
return errors.New("timed out waiting for downgrade deletion")
}
}
if dashboardChart != nil {
if dashboardExists {
if _, err = upgradeClient.Run(dashboardReleaseName, dashboardChart, vals); err != nil {
return err
}
} else {
// We need to install Dashboard since it does not exist yet.
err = install(dashboardReleaseName, conf.DashboardVersion, helmRepo, InitConfiguration{
DashboardVersion: conf.DashboardVersion,
Namespace: upgradeClient.Namespace,
Wait: upgradeClient.Wait,
Timeout: conf.Timeout,
})
if err != nil {
return err
}
}
}
return nil
}
func deleteSchedulerPods(namespace string, currentVersion *semver.Version, targetVersion *semver.Version) error {
ctxWithTimeout, cancel := context.WithTimeout(context.Background(), time.Second*30)
defer cancel()
var pods *core_v1.PodList
// wait for at least one pod of the target version to be in the list before deleting the rest
// check the label app.kubernetes.io/version to determine the version of the pod
foundTargetVersion := false
for {
if foundTargetVersion {
break
}
k8sClient, err := Client()
if err != nil {
return err
}
pods, err = k8sClient.CoreV1().Pods(namespace).List(ctxWithTimeout, meta_v1.ListOptions{
LabelSelector: "app=dapr-scheduler-server",
})
if err != nil && !errors.Is(err, context.DeadlineExceeded) {
return err
}
if len(pods.Items) == 0 {
return nil
}
for _, pod := range pods.Items {
pv, ok := pod.Labels["app.kubernetes.io/version"]
if ok {
podVersion, err := semver.NewVersion(pv)
if err == nil && podVersion.Equal(targetVersion) {
foundTargetVersion = true
break
}
}
}
time.Sleep(5 * time.Second)
}
if pods == nil {
return errors.New("no scheduler pods found")
}
// get a fresh client to ensure we have the latest state of the cluster
k8sClient, err := Client()
if err != nil {
return err
}
// delete scheduler pods of the current version, i.e. >1.15.0
for _, pod := range pods.Items {
if pv, ok := pod.Labels["app.kubernetes.io/version"]; ok {
podVersion, err := semver.NewVersion(pv)
if err == nil && podVersion.Equal(currentVersion) {
err = k8sClient.CoreV1().Pods(namespace).Delete(ctxWithTimeout, pod.Name, meta_v1.DeleteOptions{})
if err != nil {
return fmt.Errorf("failed to delete pod %s during downgrade: %w", pod.Name, err)
}
}
}
}
return nil
}
// WithRetry enables retry with the specified max retries and retry interval.
func WithRetry(maxRetries int, retryInterval time.Duration) UpgradeOption {
return func(o *UpgradeOptions) {
o.WithRetry = true
o.MaxRetries = maxRetries
o.RetryInterval = retryInterval
}
}
func helmUpgrade(client *helm.Upgrade, name string, chart *chart.Chart, vals map[string]interface{}, options ...UpgradeOption) (*release.Release, error) {
upgradeOptions := &UpgradeOptions{
WithRetry: false,
MaxRetries: 0,
RetryInterval: 0,
}
// Apply functional options.
for _, option := range options {
option(upgradeOptions)
}
var release *release.Release
for attempt := 1; ; attempt++ {
_, err := client.Run(name, chart, vals)
if err == nil {
// operation succeeded, no need to retry.
break
}
if !upgradeOptions.WithRetry || attempt >= upgradeOptions.MaxRetries {
// If not retrying or reached max retries, return the error.
return nil, fmt.Errorf("max retries reached, unable to run command: %w", err)
}
print.PendingStatusEvent(os.Stdout, "Retrying after %s...", upgradeOptions.RetryInterval)
time.Sleep(upgradeOptions.RetryInterval)
// create a totally new helm client, this ensures that we fetch a fresh openapi schema from the server on each attempt.
client, _, err = newUpgradeClient(client.Namespace, UpgradeConfig{
Timeout: uint(client.Timeout), //nolint:gosec
})
if err != nil {
return nil, fmt.Errorf("unable to create helm client: %w", err)
}
}
return release, nil
}
func highAvailabilityEnabled(status []StatusOutput) bool {
for _, s := range status {
if s.Name == "dapr-dashboard" {
continue
}
// Skip the scheduler server because it's in HA mode by default since version 1.15.0
// This will fall back to other dapr services to determine if HA mode is enabled.
if strings.HasPrefix(s.Name, "dapr-scheduler-server") {
continue
}
if s.Replicas > 1 {
return true
}
@ -144,7 +385,7 @@ func applyCRDs(version string) error {
url := fmt.Sprintf("https://raw.githubusercontent.com/dapr/dapr/%s/charts/dapr/crds/%s.yaml", version, crd)
resp, _ := http.Get(url) //nolint:gosec
if resp != nil && resp.StatusCode == 200 {
if resp != nil && resp.StatusCode == http.StatusOK {
defer resp.Body.Close()
_, err := utils.RunCmdAndWait("kubectl", "apply", "-f", url)
@ -163,18 +404,18 @@ func upgradeChartValues(ca, issuerCert, issuerKey string, haMode, mtls bool, con
if err != nil {
return nil, err
}
globalVals = append(globalVals, fmt.Sprintf("global.tag=%s", utils.GetVariantVersion(conf.RuntimeVersion, conf.ImageVariant)))
globalVals = append(globalVals, "global.tag="+utils.GetVariantVersion(conf.RuntimeVersion, conf.ImageVariant))
if mtls && ca != "" && issuerCert != "" && issuerKey != "" {
globalVals = append(globalVals, fmt.Sprintf("dapr_sentry.tls.root.certPEM=%s", ca),
fmt.Sprintf("dapr_sentry.tls.issuer.certPEM=%s", issuerCert),
fmt.Sprintf("dapr_sentry.tls.issuer.keyPEM=%s", issuerKey),
globalVals = append(globalVals, "dapr_sentry.tls.root.certPEM="+ca,
"dapr_sentry.tls.issuer.certPEM="+issuerCert,
"dapr_sentry.tls.issuer.keyPEM="+issuerKey,
)
} else {
globalVals = append(globalVals, "global.mtls.enabled=false")
}
if len(conf.ImageRegistryURI) != 0 {
globalVals = append(globalVals, fmt.Sprintf("global.registry=%s", conf.ImageRegistryURI))
globalVals = append(globalVals, "global.registry="+conf.ImageRegistryURI)
}
if haMode {
globalVals = append(globalVals, "global.ha.enabled=true")
@ -199,3 +440,19 @@ func isDowngrade(targetVersion, existingVersion string) bool {
}
return target.LessThan(existing)
}
func newUpgradeClient(namespace string, cfg UpgradeConfig) (*helm.Upgrade, *helm.Configuration, error) {
helmCfg, err := helmConfig(namespace)
if err != nil {
return nil, nil, err
}
client := helm.NewUpgrade(helmCfg)
client.ResetValues = true
client.Namespace = namespace
client.CleanupOnFail = true
client.Wait = true
client.Timeout = time.Duration(cfg.Timeout) * time.Second //nolint:gosec
return client, helmCfg, nil
}

View File

@ -31,6 +31,38 @@ func TestHAMode(t *testing.T) {
assert.True(t, r)
})
t.Run("ha mode with scheduler and other services", func(t *testing.T) {
s := []StatusOutput{
{
Name: "dapr-scheduler-server",
Replicas: 3,
},
{
Name: "dapr-placement-server",
Replicas: 3,
},
}
r := highAvailabilityEnabled(s)
assert.True(t, r)
})
t.Run("non-ha mode with only scheduler image variant", func(t *testing.T) {
s := []StatusOutput{
{
Name: "dapr-scheduler-server-mariner",
Replicas: 3,
},
{
Name: "dapr-placement-server-mariner",
Replicas: 3,
},
}
r := highAvailabilityEnabled(s)
assert.True(t, r)
})
t.Run("non-ha mode", func(t *testing.T) {
s := []StatusOutput{
{
@ -41,6 +73,46 @@ func TestHAMode(t *testing.T) {
r := highAvailabilityEnabled(s)
assert.False(t, r)
})
t.Run("non-ha mode with scheduler and other services", func(t *testing.T) {
s := []StatusOutput{
{
Name: "dapr-scheduler-server",
Replicas: 3,
},
{
Name: "dapr-placement-server",
Replicas: 1,
},
}
r := highAvailabilityEnabled(s)
assert.False(t, r)
})
t.Run("non-ha mode with only scheduler", func(t *testing.T) {
s := []StatusOutput{
{
Name: "dapr-scheduler-server",
Replicas: 3,
},
}
r := highAvailabilityEnabled(s)
assert.False(t, r)
})
t.Run("non-ha mode with only scheduler image variant", func(t *testing.T) {
s := []StatusOutput{
{
Name: "dapr-scheduler-server-mariner",
Replicas: 3,
},
}
r := highAvailabilityEnabled(s)
assert.False(t, r)
})
}
func TestMTLSChartValues(t *testing.T) {

View File

@ -75,7 +75,7 @@ func Put(httpPort int, key, value, appID, socket string) error {
url := makeMetadataPutEndpoint(httpPort, key)
req, err := retryablehttp.NewRequest("PUT", url, strings.NewReader(value))
req, err := retryablehttp.NewRequest(http.MethodPut, url, strings.NewReader(value))
if err != nil {
return err
}

View File

@ -17,6 +17,9 @@ import (
"encoding/json"
"fmt"
"io"
"os"
"reflect"
"regexp"
"runtime"
"sync"
"time"
@ -29,6 +32,16 @@ const (
windowsOS = "windows"
)
type logStatus string
const (
LogSuccess logStatus = "success"
LogFailure logStatus = "failure"
LogWarning logStatus = "warning"
LogInfo logStatus = "info"
LogPending logStatus = "pending"
)
type Result bool
const (
@ -56,10 +69,36 @@ func IsJSONLogEnabled() bool {
return logAsJSON
}
// StatusEvent reports a event log with given status.
func StatusEvent(w io.Writer, status logStatus, fmtstr string, a ...any) {
if logAsJSON {
logJSON(w, string(status), fmt.Sprintf(fmtstr, a...))
return
}
if (w != os.Stdout && w != os.Stderr) || runtime.GOOS == windowsOS {
fmt.Fprintf(w, "%s\n", fmt.Sprintf(fmtstr, a...))
return
}
switch status {
case LogSuccess:
fmt.Fprintf(w, "✅ %s\n", fmt.Sprintf(fmtstr, a...))
case LogFailure:
fmt.Fprintf(w, "❌ %s\n", fmt.Sprintf(fmtstr, a...))
case LogWarning:
fmt.Fprintf(w, "⚠ %s\n", fmt.Sprintf(fmtstr, a...))
case LogPending:
fmt.Fprintf(w, "⌛ %s\n", fmt.Sprintf(fmtstr, a...))
case LogInfo:
fmt.Fprintf(w, " %s\n", fmt.Sprintf(fmtstr, a...))
default:
fmt.Fprintf(w, "%s\n", fmt.Sprintf(fmtstr, a...))
}
}
// SuccessStatusEvent reports on a success event.
func SuccessStatusEvent(w io.Writer, fmtstr string, a ...interface{}) {
if logAsJSON {
logJSON(w, "success", fmt.Sprintf(fmtstr, a...))
logJSON(w, string(LogSuccess), fmt.Sprintf(fmtstr, a...))
} else if runtime.GOOS == windowsOS {
fmt.Fprintf(w, "%s\n", fmt.Sprintf(fmtstr, a...))
} else {
@ -70,7 +109,7 @@ func SuccessStatusEvent(w io.Writer, fmtstr string, a ...interface{}) {
// FailureStatusEvent reports on a failure event.
func FailureStatusEvent(w io.Writer, fmtstr string, a ...interface{}) {
if logAsJSON {
logJSON(w, "failure", fmt.Sprintf(fmtstr, a...))
logJSON(w, string(LogFailure), fmt.Sprintf(fmtstr, a...))
} else if runtime.GOOS == windowsOS {
fmt.Fprintf(w, "%s\n", fmt.Sprintf(fmtstr, a...))
} else {
@ -81,7 +120,7 @@ func FailureStatusEvent(w io.Writer, fmtstr string, a ...interface{}) {
// WarningStatusEvent reports on a failure event.
func WarningStatusEvent(w io.Writer, fmtstr string, a ...interface{}) {
if logAsJSON {
logJSON(w, "warning", fmt.Sprintf(fmtstr, a...))
logJSON(w, string(LogWarning), fmt.Sprintf(fmtstr, a...))
} else if runtime.GOOS == windowsOS {
fmt.Fprintf(w, "%s\n", fmt.Sprintf(fmtstr, a...))
} else {
@ -92,7 +131,7 @@ func WarningStatusEvent(w io.Writer, fmtstr string, a ...interface{}) {
// PendingStatusEvent reports on a pending event.
func PendingStatusEvent(w io.Writer, fmtstr string, a ...interface{}) {
if logAsJSON {
logJSON(w, "pending", fmt.Sprintf(fmtstr, a...))
logJSON(w, string(LogPending), fmt.Sprintf(fmtstr, a...))
} else if runtime.GOOS == windowsOS {
fmt.Fprintf(w, "%s\n", fmt.Sprintf(fmtstr, a...))
} else {
@ -103,7 +142,7 @@ func PendingStatusEvent(w io.Writer, fmtstr string, a ...interface{}) {
// InfoStatusEvent reports status information on an event.
func InfoStatusEvent(w io.Writer, fmtstr string, a ...interface{}) {
if logAsJSON {
logJSON(w, "info", fmt.Sprintf(fmtstr, a...))
logJSON(w, string(LogInfo), fmt.Sprintf(fmtstr, a...))
} else if runtime.GOOS == windowsOS {
fmt.Fprintf(w, "%s\n", fmt.Sprintf(fmtstr, a...))
} else {
@ -117,7 +156,7 @@ func Spinner(w io.Writer, fmtstr string, a ...interface{}) func(result Result) {
var s *spinner.Spinner
if logAsJSON {
logJSON(w, "pending", msg)
logJSON(w, string(LogPending), msg)
} else if runtime.GOOS == windowsOS {
fmt.Fprintf(w, "%s\n", msg)
@ -167,3 +206,37 @@ func logJSON(w io.Writer, status, message string) {
fmt.Fprintf(w, "%s\n", string(jsonBytes))
}
type CustomLogWriter struct {
W io.Writer
}
func (c CustomLogWriter) Write(p []byte) (int, error) {
write := func(w io.Writer, isStdIO bool) (int, error) {
b := p
if !isStdIO {
// below regex is used to replace the color codes from the logs collected in the log file.
reg := regexp.MustCompile("\x1b\\[[\\d;]+m")
b = reg.ReplaceAll(b, []byte(""))
}
n, err := w.Write(b)
if err != nil {
return n, err
}
if n != len(b) {
return n, io.ErrShortWrite
}
return len(b), nil
}
wIface := reflect.ValueOf(c.W).Interface()
switch wType := wIface.(type) {
case *os.File:
if wType == os.Stderr || wType == os.Stdout {
return write(c.W, true)
} else {
return write(c.W, false)
}
default:
return write(c.W, false)
}
}

View File

@ -69,7 +69,7 @@ func tryGetRunDataLock() (*lockfile.Lockfile, error) {
return nil, err
}
for i := 0; i < 10; i++ {
for range 10 {
err = lockFile.TryLock()
// Error handling is essential, as we only try to get the lock.

156
pkg/runexec/runexec.go Normal file
View File

@ -0,0 +1,156 @@
/*
Copyright 2023 The Dapr Authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package runexec
import (
"errors"
"io"
"os"
"os/exec"
"github.com/dapr/cli/pkg/runfileconfig"
"github.com/dapr/cli/pkg/standalone"
)
type CmdProcess struct {
Command *exec.Cmd
CommandErr error
OutputWriter io.Writer
ErrorWriter io.Writer
}
type RunExec struct {
DaprCMD *CmdProcess
AppCMD *CmdProcess
AppID string
DaprHTTPPort int
DaprGRPCPort int
DaprMetricPort int
}
// RunOutput represents the run execution.
type RunOutput struct {
DaprCMD *exec.Cmd
DaprErr error
DaprHTTPPort int
DaprGRPCPort int
AppID string
AppCMD *exec.Cmd
AppErr error
}
func New(config *standalone.RunConfig, daprCmdProcess *CmdProcess, appCmdProcess *CmdProcess) *RunExec {
return &RunExec{
DaprCMD: daprCmdProcess,
AppCMD: appCmdProcess,
AppID: config.AppID,
DaprHTTPPort: config.HTTPPort,
DaprGRPCPort: config.GRPCPort,
DaprMetricPort: config.MetricsPort,
}
}
func GetDaprCmdProcess(config *standalone.RunConfig) (*CmdProcess, error) {
daprCMD, err := standalone.GetDaprCommand(config)
if err != nil {
return nil, err
}
return &CmdProcess{
Command: daprCMD,
}, nil
}
func GetAppCmdProcess(config *standalone.RunConfig) (*CmdProcess, error) {
//nolint
var appCMD *exec.Cmd = standalone.GetAppCommand(config)
return &CmdProcess{
Command: appCMD,
}, nil
}
func (c *CmdProcess) WithOutputWriter(w io.Writer) {
c.OutputWriter = w
}
// SetStdout should be called after WithOutputWriter.
func (c *CmdProcess) SetStdout() error {
if c.Command == nil {
return errors.New("command is nil")
}
c.Command.Stdout = c.OutputWriter
return nil
}
func (c *CmdProcess) WithErrorWriter(w io.Writer) {
c.ErrorWriter = w
}
// SetStdErr should be called after WithErrorWriter.
func (c *CmdProcess) SetStderr() error {
if c.Command == nil {
return errors.New("command is nil")
}
c.Command.Stderr = c.ErrorWriter
return nil
}
func NewOutput(config *standalone.RunConfig) (*RunOutput, error) {
// set default values from RunConfig struct's tag.
config.SetDefaultFromSchema()
err := config.Validate()
if err != nil {
return nil, err
}
daprCMD, err := standalone.GetDaprCommand(config)
if err != nil {
return nil, err
}
//nolint
var appCMD *exec.Cmd = standalone.GetAppCommand(config)
return &RunOutput{
DaprCMD: daprCMD,
DaprErr: nil,
AppCMD: appCMD,
AppErr: nil,
AppID: config.AppID,
DaprHTTPPort: config.HTTPPort,
DaprGRPCPort: config.GRPCPort,
}, nil
}
// GetAppDaprdWriter returns the writer for writing logs common to both daprd, app and stdout.
func GetAppDaprdWriter(app runfileconfig.App, isAppCommandEmpty bool) io.Writer {
var appDaprdWriter io.Writer
if isAppCommandEmpty {
if app.DaprdLogDestination != standalone.Console {
appDaprdWriter = io.MultiWriter(os.Stdout, app.DaprdLogWriteCloser)
} else {
appDaprdWriter = os.Stdout
}
} else {
if app.AppLogDestination != standalone.Console && app.DaprdLogDestination != standalone.Console {
appDaprdWriter = io.MultiWriter(app.AppLogWriteCloser, app.DaprdLogWriteCloser, os.Stdout)
} else if app.AppLogDestination != standalone.Console {
appDaprdWriter = io.MultiWriter(app.AppLogWriteCloser, os.Stdout)
} else if app.DaprdLogDestination != standalone.Console {
appDaprdWriter = io.MultiWriter(app.DaprdLogWriteCloser, os.Stdout)
} else {
appDaprdWriter = os.Stdout
}
}
return appDaprdWriter
}

369
pkg/runexec/runexec_test.go Normal file
View File

@ -0,0 +1,369 @@
/*
Copyright 2023 The Dapr Authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package runexec
import (
"fmt"
"os"
"regexp"
"strings"
"testing"
"github.com/stretchr/testify/require"
"github.com/stretchr/testify/assert"
"github.com/dapr/cli/pkg/standalone"
)
func assertArgumentEqual(t *testing.T, key string, expectedValue string, args []string) {
var value string
for index, arg := range args {
if arg == "--"+key {
nextIndex := index + 1
if nextIndex < len(args) {
if !strings.HasPrefix(args[nextIndex], "--") {
value = args[nextIndex]
}
}
}
}
assert.Equal(t, expectedValue, value)
}
func assertArgumentNotEqual(t *testing.T, key string, expectedValue string, args []string) {
var value string
for index, arg := range args {
if arg == "--"+key {
nextIndex := index + 1
if nextIndex < len(args) {
if !strings.HasPrefix(args[nextIndex], "--") {
value = args[nextIndex]
}
}
}
}
assert.NotEqual(t, expectedValue, value)
}
func assertArgumentContains(t *testing.T, key string, expectedValue string, args []string) {
var value string
for index, arg := range args {
if arg == "--"+key {
nextIndex := index + 1
if nextIndex < len(args) {
if !strings.HasPrefix(args[nextIndex], "--") {
value = args[nextIndex]
}
}
}
}
assert.Contains(t, value, expectedValue)
}
func setupRun(t *testing.T) {
myDaprPath, err := standalone.GetDaprRuntimePath("")
assert.NoError(t, err)
componentsDir := standalone.GetDaprComponentsPath(myDaprPath)
configFile := standalone.GetDaprConfigPath(myDaprPath)
err = os.MkdirAll(componentsDir, 0o700)
assert.NoError(t, err, "Unable to setup components dir before running test")
file, err := os.Create(configFile)
file.Close()
assert.NoError(t, err, "Unable to create config file before running test")
}
func tearDownRun(t *testing.T) {
myDaprPath, err := standalone.GetDaprRuntimePath("")
assert.NoError(t, err)
componentsDir := standalone.GetDaprComponentsPath(myDaprPath)
configFile := standalone.GetDaprConfigPath(myDaprPath)
err = os.RemoveAll(componentsDir)
assert.NoError(t, err, "Unable to delete default components dir after running test")
err = os.Remove(configFile)
assert.NoError(t, err, "Unable to delete default config file after running test")
}
func assertCommonArgs(t *testing.T, basicConfig *standalone.RunConfig, output *RunOutput) {
assert.NotNil(t, output)
assert.Equal(t, "MyID", output.AppID)
assert.Equal(t, 8000, output.DaprHTTPPort)
assert.Equal(t, 50001, output.DaprGRPCPort)
daprPath, err := standalone.GetDaprRuntimePath("")
assert.NoError(t, err)
assert.Contains(t, output.DaprCMD.Args[0], "daprd")
assertArgumentEqual(t, "app-id", "MyID", output.DaprCMD.Args)
assertArgumentEqual(t, "dapr-http-port", "8000", output.DaprCMD.Args)
assertArgumentEqual(t, "dapr-grpc-port", "50001", output.DaprCMD.Args)
assertArgumentEqual(t, "log-level", basicConfig.LogLevel, output.DaprCMD.Args)
assertArgumentEqual(t, "app-max-concurrency", "-1", output.DaprCMD.Args)
assertArgumentEqual(t, "app-protocol", "http", output.DaprCMD.Args)
assertArgumentEqual(t, "app-port", "3000", output.DaprCMD.Args)
assertArgumentEqual(t, "components-path", standalone.GetDaprComponentsPath(daprPath), output.DaprCMD.Args)
assertArgumentEqual(t, "app-ssl", "", output.DaprCMD.Args)
assertArgumentEqual(t, "metrics-port", "9001", output.DaprCMD.Args)
assertArgumentEqual(t, "max-body-size", "-1", output.DaprCMD.Args)
assertArgumentEqual(t, "dapr-internal-grpc-port", "5050", output.DaprCMD.Args)
assertArgumentEqual(t, "read-buffer-size", "-1", output.DaprCMD.Args)
assertArgumentEqual(t, "dapr-listen-addresses", "127.0.0.1", output.DaprCMD.Args)
}
func assertAppEnv(t *testing.T, config *standalone.RunConfig, output *RunOutput) {
envSet := make(map[string]bool)
for _, env := range output.AppCMD.Env {
envSet[env] = true
}
expectedEnvSet := getEnvSet(config)
for _, env := range expectedEnvSet {
_, found := envSet[env]
if !found {
assert.Fail(t, "Missing environment variable. Expected to have "+env)
}
}
}
func getEnvSet(config *standalone.RunConfig) []string {
set := []string{
getEnv("DAPR_GRPC_PORT", config.GRPCPort),
getEnv("DAPR_HTTP_PORT", config.HTTPPort),
getEnv("DAPR_METRICS_PORT", config.MetricsPort),
getEnv("APP_ID", config.AppID),
}
if config.AppPort > 0 {
set = append(set, getEnv("APP_PORT", config.AppPort))
}
if config.EnableProfiling {
set = append(set, getEnv("DAPR_PROFILE_PORT", config.ProfilePort))
}
return set
}
func getEnv(key string, value interface{}) string {
return fmt.Sprintf("%s=%v", key, value)
}
func TestRun(t *testing.T) {
// Setup the components directory which is done at init time.
setupRun(t)
// Setup the tearDown routine to run in the end.
defer tearDownRun(t)
myDaprPath, err := standalone.GetDaprRuntimePath("")
assert.NoError(t, err)
componentsDir := standalone.GetDaprComponentsPath(myDaprPath)
configFile := standalone.GetDaprConfigPath(myDaprPath)
sharedRunConfig := &standalone.SharedRunConfig{
LogLevel: "WARN",
EnableProfiling: false,
AppProtocol: "http",
ComponentsPath: componentsDir,
AppSSL: true,
MaxRequestBodySize: "-1",
HTTPReadBufferSize: "-1",
EnableAPILogging: true,
APIListenAddresses: "127.0.0.1",
}
basicConfig := &standalone.RunConfig{
AppID: "MyID",
AppPort: 3000,
HTTPPort: 8000,
GRPCPort: 50001,
Command: []string{"MyCommand", "--my-arg"},
ProfilePort: 9090,
MetricsPort: 9001,
InternalGRPCPort: 5050,
AppChannelAddress: "localhost",
SharedRunConfig: *sharedRunConfig,
}
t.Run("run happy http", func(t *testing.T) {
output, err := NewOutput(basicConfig)
assert.NoError(t, err)
assertCommonArgs(t, basicConfig, output)
assert.Equal(t, "MyCommand", output.AppCMD.Args[0])
assert.Equal(t, "--my-arg", output.AppCMD.Args[1])
assertArgumentEqual(t, "app-channel-address", "localhost", output.DaprCMD.Args)
assertAppEnv(t, basicConfig, output)
})
t.Run("run without app command", func(t *testing.T) {
basicConfig.Command = nil
basicConfig.LogLevel = "INFO"
basicConfig.EnableAPILogging = true
basicConfig.ConfigFile = configFile
output, err := NewOutput(basicConfig)
assert.NoError(t, err)
assertCommonArgs(t, basicConfig, output)
assertArgumentContains(t, "config", standalone.DefaultConfigFileName, output.DaprCMD.Args)
assert.Nil(t, output.AppCMD)
})
t.Run("run without port", func(t *testing.T) {
basicConfig.HTTPPort = -1
basicConfig.GRPCPort = -1
basicConfig.MetricsPort = -1
output, err := NewOutput(basicConfig)
assert.NoError(t, err)
assert.NotNil(t, output)
assertArgumentNotEqual(t, "http-port", "-1", output.DaprCMD.Args)
assertArgumentNotEqual(t, "grpc-port", "-1", output.DaprCMD.Args)
assertArgumentNotEqual(t, "metrics-port", "-1", output.DaprCMD.Args)
})
t.Run("app health check flags missing if not set", func(t *testing.T) {
output, err := NewOutput(basicConfig)
assert.NoError(t, err)
assert.NotNil(t, output)
argsFlattened := strings.Join(output.DaprCMD.Args, " ")
assert.NotRegexp(t, regexp.MustCompile(`( |^)--enable-app-health-check( |$)`), argsFlattened)
assert.NotRegexp(t, regexp.MustCompile(`( |^)--app-health-check-path( |=)`), argsFlattened)
assert.NotRegexp(t, regexp.MustCompile(`( |^)--app-health-probe-interval( |=)`), argsFlattened)
assert.NotRegexp(t, regexp.MustCompile(`( |^)--app-health-probe-timeout( |=)`), argsFlattened)
assert.NotRegexp(t, regexp.MustCompile(`( |^)--app-health-threshold( |=)`), argsFlattened)
})
t.Run("enable app health checks with default flags", func(t *testing.T) {
basicConfig.EnableAppHealth = true
output, err := NewOutput(basicConfig)
assert.NoError(t, err)
assert.NotNil(t, output)
argsFlattened := strings.Join(output.DaprCMD.Args, " ")
assert.Regexp(t, regexp.MustCompile(`( |^)--enable-app-health-check( |$)`), argsFlattened)
// Other flags are not included so daprd can use the default value.
assert.NotRegexp(t, regexp.MustCompile(`( |^)--app-health-check-path( |=)`), argsFlattened)
assert.NotRegexp(t, regexp.MustCompile(`( |^)--app-health-probe-interval( |=)`), argsFlattened)
assert.NotRegexp(t, regexp.MustCompile(`( |^)--app-health-probe-timeout( |=)`), argsFlattened)
assert.NotRegexp(t, regexp.MustCompile(`( |^)--app-health-threshold( |=)`), argsFlattened)
})
t.Run("enable app health checks with all flags set", func(t *testing.T) {
basicConfig.EnableAppHealth = true
basicConfig.AppHealthInterval = 2
basicConfig.AppHealthTimeout = 200
basicConfig.AppHealthThreshold = 1
basicConfig.AppHealthPath = "/foo"
output, err := NewOutput(basicConfig)
assert.NoError(t, err)
assert.NotNil(t, output)
argsFlattened := strings.Join(output.DaprCMD.Args, " ")
assert.Regexp(t, regexp.MustCompile(`( |^)--enable-app-health-check( |$)`), argsFlattened)
assert.Regexp(t, regexp.MustCompile(`( |^)--app-health-check-path( |=)/foo`), argsFlattened)
assert.Regexp(t, regexp.MustCompile(`( |^)--app-health-probe-interval( |=)2`), argsFlattened)
assert.Regexp(t, regexp.MustCompile(`( |^)--app-health-probe-timeout( |=)200`), argsFlattened)
assert.Regexp(t, regexp.MustCompile(`( |^)--app-health-threshold( |=)1`), argsFlattened)
})
t.Run("test setting defaults from struct tag", func(t *testing.T) {
basicConfig.AppPort = 0
basicConfig.HTTPPort = 0
basicConfig.GRPCPort = 0
basicConfig.MetricsPort = 0
basicConfig.ProfilePort = 0
basicConfig.EnableProfiling = true
basicConfig.MaxConcurrency = 0
basicConfig.MaxRequestBodySize = ""
basicConfig.HTTPReadBufferSize = ""
basicConfig.AppProtocol = ""
basicConfig.SetDefaultFromSchema()
assert.Equal(t, -1, basicConfig.AppPort)
assert.Equal(t, -1, basicConfig.HTTPPort)
assert.Equal(t, -1, basicConfig.GRPCPort)
assert.Equal(t, -1, basicConfig.MetricsPort)
assert.Equal(t, -1, basicConfig.ProfilePort)
assert.True(t, basicConfig.EnableProfiling)
assert.Equal(t, -1, basicConfig.MaxConcurrency)
assert.Equal(t, "4Mi", basicConfig.MaxRequestBodySize)
assert.Equal(t, "4Ki", basicConfig.HTTPReadBufferSize)
assert.Equal(t, "http", basicConfig.AppProtocol)
// Test after Validate gets called.
err := basicConfig.Validate()
assert.NoError(t, err)
assert.Equal(t, 0, basicConfig.AppPort)
assert.Positive(t, basicConfig.HTTPPort)
assert.Positive(t, basicConfig.GRPCPort)
assert.Positive(t, basicConfig.MetricsPort)
assert.Positive(t, basicConfig.ProfilePort)
assert.True(t, basicConfig.EnableProfiling)
assert.Equal(t, -1, basicConfig.MaxConcurrency)
assert.Equal(t, "4Mi", basicConfig.MaxRequestBodySize)
assert.Equal(t, "4Ki", basicConfig.HTTPReadBufferSize)
assert.Equal(t, "http", basicConfig.AppProtocol)
})
t.Run("run with max body size without units", func(t *testing.T) {
basicConfig.MaxRequestBodySize = "4000000"
output, err := NewOutput(basicConfig)
require.NoError(t, err)
assertArgumentEqual(t, "max-body-size", "4M", output.DaprCMD.Args)
})
t.Run("run with max body size with units", func(t *testing.T) {
basicConfig.MaxRequestBodySize = "4Mi"
output, err := NewOutput(basicConfig)
require.NoError(t, err)
assertArgumentEqual(t, "max-body-size", "4Mi", output.DaprCMD.Args)
basicConfig.MaxRequestBodySize = "5M"
output, err = NewOutput(basicConfig)
require.NoError(t, err)
assertArgumentEqual(t, "max-body-size", "5M", output.DaprCMD.Args)
})
t.Run("run with read buffer size set without units", func(t *testing.T) {
basicConfig.HTTPReadBufferSize = "16001"
output, err := NewOutput(basicConfig)
require.NoError(t, err)
assertArgumentEqual(t, "read-buffer-size", "16001", output.DaprCMD.Args)
})
t.Run("run with read buffer size set with units", func(t *testing.T) {
basicConfig.HTTPReadBufferSize = "4Ki"
output, err := NewOutput(basicConfig)
require.NoError(t, err)
assertArgumentEqual(t, "read-buffer-size", "4Ki", output.DaprCMD.Args)
})
}

View File

@ -0,0 +1,150 @@
/*
Copyright 2022 The Dapr Authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package runfileconfig
import (
"io"
"os"
"path/filepath"
"time"
"github.com/dapr/cli/pkg/standalone"
)
const (
appLogFileNamePrefix = "app"
daprdLogFileNamePrefix = "daprd"
logFileExtension = ".log"
logsDir = "logs"
deployDir = "deploy"
)
// RunFileConfig represents the complete configuration options for the run file.
// It is meant to be used with - "dapr run --run-file <path-to-run-file>" command.
type RunFileConfig struct {
Common Common `yaml:"common"`
Apps []App `yaml:"apps"`
Version int `yaml:"version"`
Name string `yaml:"name,omitempty"`
}
// ContainerConfiguration represents the application container configuration parameters.
type ContainerConfiguration struct {
ContainerImage string `yaml:"containerImage"`
ContainerImagePullPolicy string `yaml:"containerImagePullPolicy"`
CreateService bool `yaml:"createService"`
}
// App represents the configuration options for the apps in the run file.
type App struct {
standalone.RunConfig `yaml:",inline"`
ContainerConfiguration `yaml:",inline"`
AppDirPath string `yaml:"appDirPath"`
AppLogFileName string
DaprdLogFileName string
AppLogWriteCloser io.WriteCloser
DaprdLogWriteCloser io.WriteCloser
}
// Common represents the configuration options for the common section in the run file.
type Common struct {
standalone.SharedRunConfig `yaml:",inline"`
}
func (a *App) GetLogsDir() string {
logsPath := filepath.Join(a.AppDirPath, standalone.DefaultDaprDirName, logsDir)
os.MkdirAll(logsPath, 0o755)
return logsPath
}
func (a *App) GetDeployDir() string {
logsPath := filepath.Join(a.AppDirPath, standalone.DefaultDaprDirName, deployDir)
os.MkdirAll(logsPath, 0o755)
return logsPath
}
// CreateAppLogFile creates the log file, sets internal file handle
// and returns error if any.
func (a *App) CreateAppLogFile() error {
var err error
var f *os.File
if a.AppLogDestination == standalone.Console {
f = os.Stdout
} else {
f, err = a.createLogFile(appLogFileNamePrefix)
}
if err == nil {
a.AppLogWriteCloser = f
a.AppLogFileName = f.Name()
}
return err
}
// CreateDaprdLogFile creates the log file, sets internal file handle
// and returns error if any.
func (a *App) CreateDaprdLogFile() error {
var err error
var f *os.File
if a.DaprdLogDestination == standalone.Console {
f = os.Stdout
} else {
f, err = a.createLogFile(daprdLogFileNamePrefix)
}
if err == nil {
a.DaprdLogWriteCloser = f
a.DaprdLogFileName = f.Name()
}
return err
}
// createLogFile creates the log file and returns the file handle and error if any.
// It also adds the app ID as a prefix and the current timestamp to the file name as a suffix.
func (a *App) createLogFile(logType string) (*os.File, error) {
logsPath := a.GetLogsDir()
fpath := filepath.Join(logsPath, a.AppID+"_"+logType+"_"+time.Now().Format("20060102150405")+logFileExtension)
f, err := os.Create(fpath)
return f, err
}
func (a *App) CloseAppLogFile() error {
if a.AppLogWriteCloser != nil {
err := a.AppLogWriteCloser.Close()
a.AppLogWriteCloser = nil
return err
}
return nil
}
func (a *App) CloseDaprdLogFile() error {
if a.DaprdLogWriteCloser != nil {
err := a.DaprdLogWriteCloser.Close()
a.DaprdLogWriteCloser = nil
return err
}
return nil
}
// GetLogWriter returns the log writer based on the log destination.
func GetLogWriter(fileLogWriterCloser io.WriteCloser, logDestination standalone.LogDestType) io.Writer {
var logWriter io.Writer
switch logDestination {
case standalone.Console:
logWriter = os.Stdout
case standalone.File:
logWriter = fileLogWriterCloser
case standalone.FileAndConsole:
logWriter = io.MultiWriter(os.Stdout, fileLogWriterCloser)
}
return logWriter
}

View File

@ -0,0 +1,308 @@
/*
Copyright 2022 The Dapr Authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package runfileconfig
import (
"errors"
"fmt"
"path/filepath"
"reflect"
"strings"
"github.com/dapr/cli/pkg/standalone"
"github.com/dapr/cli/utils"
"gopkg.in/yaml.v2"
)
var imagePullPolicyValuesAllowed = []string{"Always", "Never", "IfNotPresent"}
// Parse the provided run file into a RunFileConfig struct.
func (a *RunFileConfig) parseAppsConfig(runFilePath string) error {
var err error
bytes, err := utils.ReadFile(runFilePath)
if err != nil {
return err
}
err = yaml.Unmarshal(bytes, &a)
if err != nil {
return fmt.Errorf("error in parsing the provided app config file: %w", err)
}
return nil
}
// validateRunConfig validates the run file config for mandatory fields.
// It also resolves relative paths to absolute paths and validates them.
func (a *RunFileConfig) validateRunConfig(runFilePath string) error {
baseDir, err := filepath.Abs(filepath.Dir(runFilePath))
if err != nil {
return fmt.Errorf("error in getting the absolute path of the provided run template file: %w", err)
}
if a.Version == 0 {
return errors.New("required field 'version' not found in the provided run template file")
}
// resolve relative path to absolute and validate all paths in commons.
err = a.resolvePathToAbsAndValidate(baseDir, &a.Common.ConfigFile, &a.Common.ResourcesPath, &a.Common.DaprdInstallPath)
if err != nil {
return err
}
// Resolves common's section ResourcesPaths to absolute paths and validates them.
for i := range a.Common.ResourcesPaths {
err := a.resolvePathToAbsAndValidate(baseDir, &a.Common.ResourcesPaths[i])
if err != nil {
return err
}
}
// Merge common's section ResourcesPaths and ResourcePath. ResourcesPaths will be single source of truth for resources to be loaded.
if len(strings.TrimSpace(a.Common.ResourcesPath)) > 0 {
a.Common.ResourcesPaths = append(a.Common.ResourcesPaths, a.Common.ResourcesPath)
}
for i := range len(a.Apps) {
if a.Apps[i].AppDirPath == "" {
return errors.New("required field 'appDirPath' not found in the provided app config file")
}
// It resolves the relative AppDirPath to absolute path and validates it.
err := a.resolvePathToAbsAndValidate(baseDir, &a.Apps[i].AppDirPath)
if err != nil {
return err
}
// All other relative paths present inside the specific app's in the YAML file, should be resolved relative to AppDirPath for that app.
err = a.resolvePathToAbsAndValidate(a.Apps[i].AppDirPath, &a.Apps[i].ConfigFile, &a.Apps[i].ResourcesPath, &a.Apps[i].DaprdInstallPath)
if err != nil {
return err
}
// Resolves ResourcesPaths to absolute paths and validates them.
for j := range a.Apps[i].ResourcesPaths {
err := a.resolvePathToAbsAndValidate(a.Apps[i].AppDirPath, &a.Apps[i].ResourcesPaths[j])
if err != nil {
return err
}
}
// Merge app's section ResourcesPaths and ResourcePath. ResourcesPaths will be single source of truth for resources to be loaded.
if len(strings.TrimSpace(a.Apps[i].ResourcesPath)) > 0 {
a.Apps[i].ResourcesPaths = append(a.Apps[i].ResourcesPaths, a.Apps[i].ResourcesPath)
}
// Check containerImagePullPolicy is valid.
if a.Apps[i].ContainerImagePullPolicy != "" {
if !utils.Contains(imagePullPolicyValuesAllowed, a.Apps[i].ContainerImagePullPolicy) {
return fmt.Errorf("invalid containerImagePullPolicy: %s, allowed values: %s", a.Apps[i].ContainerImagePullPolicy, strings.Join(imagePullPolicyValuesAllowed, ", "))
}
} else {
a.Apps[i].ContainerImagePullPolicy = "Always"
}
}
return nil
}
// GetApps orchestrates the parsing of supplied run file, validating fields and consolidating SharedRunConfig for the apps.
// It returns a list of apps with the merged values for the SharedRunConfig from common section of the YAML file.
func (a *RunFileConfig) GetApps(runFilePath string) ([]App, error) {
err := a.parseAppsConfig(runFilePath)
if err != nil {
return nil, err
}
err = a.validateRunConfig(runFilePath)
if err != nil {
return nil, err
}
err = a.resolveResourcesAndConfigFilePaths()
if err != nil {
return nil, err
}
a.mergeCommonAndAppsSharedRunConfig()
a.mergeCommonAndAppsEnv()
// Set and validates default fields in the run file.
err = a.setDefaultFields()
if err != nil {
return nil, err
}
return a.Apps, nil
}
// mergeCommonAndAppsSharedRunConfig merges the common section of the run file with the apps section.
func (a *RunFileConfig) mergeCommonAndAppsSharedRunConfig() {
sharedConfigType := reflect.TypeOf(a.Common.SharedRunConfig)
fields := reflect.VisibleFields(sharedConfigType)
// Iterate for each field in common(shared configurations).
for _, field := range fields {
val := reflect.ValueOf(a.Common.SharedRunConfig).FieldByName(field.Name)
// Iterate for each app's configurations.
for i := range a.Apps {
appVal := reflect.ValueOf(a.Apps[i].RunConfig.SharedRunConfig).FieldByName(field.Name)
// If apppVal is the default value for the type.
if appVal.IsZero() {
// Here FieldByName always returns a valid value, it can also be zero but the field always exists.
reflect.ValueOf(&a.Apps[i].RunConfig.SharedRunConfig).
Elem().
FieldByName(field.Name).
Set(val)
}
}
}
}
// setDefaultFields sets the default values for the fields that are not provided in the run file.
func (a *RunFileConfig) setDefaultFields() error {
for i := range a.Apps {
if err := a.setAppIDIfEmpty(&a.Apps[i]); err != nil {
return err
}
if err := a.setAndValidateLogDestination(&a.Apps[i]); err != nil {
return err
}
}
return nil
}
// Set AppID to the directory name of appDirPath.
// appDirPath is a mandatory field in the run file and at this point it is already validated and resolved to its absolute path.
func (a *RunFileConfig) setAppIDIfEmpty(app *App) error {
if app.AppID == "" {
basePath, err := a.getBasePathFromAbsPath(app.AppDirPath)
if err != nil {
return fmt.Errorf("error in setting the app id: %w", err)
}
app.AppID = basePath
}
return nil
}
// setAndValidateLogDestination sets the default log destination if not provided in the run file.
// It also validates the log destination if provided.
func (a *RunFileConfig) setAndValidateLogDestination(app *App) error {
if app.DaprdLogDestination == "" {
app.DaprdLogDestination = standalone.DefaultDaprdLogDest
} else if err := app.DaprdLogDestination.IsValid(); err != nil {
return err
}
if app.AppLogDestination == "" {
app.AppLogDestination = standalone.DefaultAppLogDest
} else if err := app.AppLogDestination.IsValid(); err != nil {
return err
}
return nil
}
// Gets the base path from the absolute path of the appDirPath.
func (a *RunFileConfig) getBasePathFromAbsPath(appDirPath string) (string, error) {
if filepath.IsAbs(appDirPath) {
return filepath.Base(appDirPath), nil
}
return "", fmt.Errorf("error in getting the base path from the provided appDirPath %q: ", appDirPath)
}
// resolvePathToAbsAndValidate resolves the relative paths in run file to absolute path and validates the file path.
func (a *RunFileConfig) resolvePathToAbsAndValidate(baseDir string, paths ...*string) error {
var err error
for _, path := range paths {
if *path == "" {
continue
}
*path, err = utils.ResolveHomeDir(*path)
if err != nil {
return err
}
absPath := utils.GetAbsPath(baseDir, *path)
*path = absPath
if err = utils.ValidateFilePath(*path); err != nil {
return err
}
}
return nil
}
// Resolve resources and config file paths for each app.
func (a *RunFileConfig) resolveResourcesAndConfigFilePaths() error {
for i := range a.Apps {
app := &a.Apps[i]
// Make sure apps's "DaprPathCmdFlag" is updated here as it is used in deciding precedence for resources and config path.
if app.DaprdInstallPath == "" {
app.DaprdInstallPath = a.Common.DaprdInstallPath
}
err := a.resolveResourcesFilePath(app)
if err != nil {
return fmt.Errorf("error in resolving resources path for app %q: %w", app.AppID, err)
}
err = a.resolveConfigFilePath(app)
if err != nil {
return fmt.Errorf("error in resolving config file path for app %q: %w", app.AppID, err)
}
}
return nil
}
// mergeCommonAndAppsEnv merges env maps from common and individual apps.
// Precedence order for envs -> apps[i].envs > common.envs.
func (a *RunFileConfig) mergeCommonAndAppsEnv() {
for i := range a.Apps {
for k, v := range a.Common.Env {
if _, ok := a.Apps[i].Env[k]; !ok {
a.Apps[i].Env[k] = v
}
}
}
}
// resolveResourcesFilePath resolves the resources path for the app.
// Precedence order for resourcesPaths -> apps[i].resourcesPaths > apps[i].appDirPath/.dapr/resources > common.resourcesPaths > dapr default resources path.
func (a *RunFileConfig) resolveResourcesFilePath(app *App) error {
if len(app.ResourcesPaths) > 0 {
return nil
}
localResourcesDir := filepath.Join(app.AppDirPath, standalone.DefaultDaprDirName, standalone.DefaultResourcesDirName)
if err := utils.ValidateFilePath(localResourcesDir); err == nil {
app.ResourcesPaths = []string{localResourcesDir}
} else if len(a.Common.ResourcesPaths) > 0 {
app.ResourcesPaths = append(app.ResourcesPaths, a.Common.ResourcesPaths...)
} else {
daprDirPath, err := standalone.GetDaprRuntimePath(app.DaprdInstallPath)
if err != nil {
return fmt.Errorf("error getting dapr install path: %w", err)
}
app.ResourcesPaths = []string{standalone.GetDaprComponentsPath(daprDirPath)}
}
return nil
}
// resolveConfigFilePath resolves the config file path for the app.
// Precedence order for configFile -> apps[i].configFile > apps[i].appDirPath/.dapr/config.yaml > common.configFile > dapr default config file.
func (a *RunFileConfig) resolveConfigFilePath(app *App) error {
if app.ConfigFile != "" {
return nil
}
localConfigFile := filepath.Join(app.AppDirPath, standalone.DefaultDaprDirName, standalone.DefaultConfigFileName)
if err := utils.ValidateFilePath(localConfigFile); err == nil {
app.ConfigFile = localConfigFile
} else if len(strings.TrimSpace(a.Common.ConfigFile)) > 0 {
app.ConfigFile = a.Common.ConfigFile
} else {
daprDirPath, err := standalone.GetDaprRuntimePath(app.DaprdInstallPath)
if err != nil {
return fmt.Errorf("error getting dapr install path: %w", err)
}
app.ConfigFile = standalone.GetDaprConfigPath(daprDirPath)
}
return nil
}

View File

@ -0,0 +1,407 @@
/*
Copyright 2022 The Dapr Authors
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package runfileconfig
import (
"fmt"
"os"
"path/filepath"
"strings"
"testing"
"github.com/dapr/cli/pkg/standalone"
"github.com/stretchr/testify/assert"
)
var (
validRunFilePath = filepath.Join(".", "testdata", "test_run_config.yaml")
invalidRunFilePath1 = filepath.Join(".", "testdata", "test_run_config_invalid_path.yaml")
invalidRunFilePath2 = filepath.Join(".", "testdata", "test_run_config_empty_app_dir.yaml")
runFileForPrecedenceRule = filepath.Join(".", "testdata", "test_run_config_precedence_rule.yaml")
runFileForPrecedenceRuleDaprDir = filepath.Join(".", "testdata", "test_run_config_precedence_rule_dapr_dir.yaml")
runFileForLogDestination = filepath.Join(".", "testdata", "test_run_config_log_destination.yaml")
runFileForMultiResourcePaths = filepath.Join(".", "testdata", "test_run_config_multiple_resources_paths.yaml")
runFileForContainerImagePullPolicy = filepath.Join(".", "testdata", "test_run_config_container_image_pull_policy.yaml")
runFileForContainerImagePullPolicyInvalid = filepath.Join(".", "testdata", "test_run_config_container_image_pull_policy_invalid.yaml")
)
func TestRunConfigFile(t *testing.T) {
t.Parallel()
t.Run("test parse valid run template", func(t *testing.T) {
appsRunConfig := RunFileConfig{}
err := appsRunConfig.parseAppsConfig(validRunFilePath)
assert.NoError(t, err)
assert.Len(t, appsRunConfig.Apps, 2)
assert.Equal(t, 1, appsRunConfig.Version)
assert.NotEmpty(t, appsRunConfig.Common.ResourcesPath)
assert.NotEmpty(t, appsRunConfig.Common.Env)
firstAppConfig := appsRunConfig.Apps[0]
secondAppConfig := appsRunConfig.Apps[1]
assert.Equal(t, "", firstAppConfig.AppID)
assert.Equal(t, "GRPC", secondAppConfig.AppProtocol)
assert.Equal(t, 8080, firstAppConfig.AppPort)
assert.Equal(t, "", firstAppConfig.UnixDomainSocket)
})
t.Run("test GetApps", func(t *testing.T) {
config := RunFileConfig{}
apps, err := config.GetApps(validRunFilePath)
assert.NoError(t, err)
assert.Len(t, apps, 2)
assert.Equal(t, "webapp", apps[0].AppID)
assert.Equal(t, "backend", apps[1].AppID)
assert.Equal(t, "HTTP", apps[0].AppProtocol)
assert.Equal(t, "GRPC", apps[1].AppProtocol)
assert.Equal(t, 8080, apps[0].AppPort)
assert.Equal(t, 3000, apps[1].AppPort)
assert.Equal(t, 1, apps[0].AppHealthTimeout)
assert.Equal(t, 10, apps[1].AppHealthTimeout)
assert.Equal(t, "", apps[0].UnixDomainSocket)
assert.Equal(t, "/tmp/test-socket", apps[1].UnixDomainSocket)
// test resourcesPath and configPath after precedence order logic.
assert.Equal(t, filepath.Join(apps[0].AppDirPath, "resources"), apps[0].ResourcesPaths[0])
assert.Equal(t, filepath.Join(apps[1].AppDirPath, ".dapr", "resources"), apps[1].ResourcesPaths[0])
assert.Equal(t, filepath.Join(apps[0].AppDirPath, "config.yaml"), apps[0].ConfigFile)
assert.Equal(t, filepath.Join(apps[1].AppDirPath, ".dapr", "config.yaml"), apps[1].ConfigFile)
// temporarily set apps[0].ResourcesPath to empty string to test it is getting picked from common section.
apps[0].ResourcesPaths = []string{}
config.resolveResourcesAndConfigFilePaths()
assert.Equal(t, config.Common.ResourcesPaths[0], apps[0].ResourcesPaths[0])
assert.Equal(t, filepath.Join(apps[1].AppDirPath, ".dapr", "resources"), apps[1].ResourcesPaths[0])
// test merged envs from common and app sections.
assert.Len(t, apps[0].Env, 2)
assert.Len(t, apps[1].Env, 2)
assert.Contains(t, apps[0].Env, "DEBUG")
assert.Contains(t, apps[0].Env, "tty")
assert.Contains(t, apps[1].Env, "DEBUG")
assert.Contains(t, apps[1].Env, "tty")
assert.Equal(t, "false", apps[0].Env["DEBUG"])
assert.Equal(t, "sts", apps[0].Env["tty"])
assert.Equal(t, "true", apps[1].Env["DEBUG"])
assert.Equal(t, "sts", apps[1].Env["tty"])
})
t.Run("test precedence logic for resources-path and dapr config file", func(t *testing.T) {
config := RunFileConfig{}
err := config.parseAppsConfig(runFileForPrecedenceRule)
assert.NoError(t, err)
err = config.validateRunConfig(runFileForPrecedenceRule)
assert.NoError(t, err)
// test precedence logic for resourcesPath and configPath.
err = config.resolveResourcesAndConfigFilePaths()
assert.NoError(t, err)
testcases := []struct {
name string
expectedResourcesPath string
expectedConfigFilePath string
appIndex int
}{
{
name: "resourcesPaths and configPath are set in app section",
expectedResourcesPath: filepath.Join(config.Apps[0].AppDirPath, "resources"),
expectedConfigFilePath: filepath.Join(config.Apps[0].AppDirPath, "config.yaml"),
appIndex: 0,
},
{
name: "resourcesPaths and configPath present in .dapr directory under appDirPath",
expectedResourcesPath: filepath.Join(config.Apps[1].AppDirPath, ".dapr", "resources"),
expectedConfigFilePath: filepath.Join(config.Apps[1].AppDirPath, ".dapr", "config.yaml"),
appIndex: 1,
},
{
name: "resourcesPaths and configPath are resolved from common's section",
expectedResourcesPath: config.Common.ResourcesPaths[0], // from common section.
expectedConfigFilePath: config.Common.ConfigFile, // from common section.
appIndex: 2,
},
}
for _, tc := range testcases {
t.Run(tc.name, func(t *testing.T) {
assert.Equal(t, tc.expectedResourcesPath, config.Apps[tc.appIndex].ResourcesPaths[0])
assert.Equal(t, tc.expectedConfigFilePath, config.Apps[tc.appIndex].ConfigFile)
})
}
})
t.Run("test precedence logic with daprInstallDir for resources-path and dapr config file", func(t *testing.T) {
config := RunFileConfig{}
err := config.parseAppsConfig(runFileForPrecedenceRuleDaprDir)
assert.NoError(t, err)
err = config.validateRunConfig(runFileForPrecedenceRuleDaprDir)
assert.NoError(t, err)
app1Data := getResourcesAndConfigFilePaths(t, config.Apps[0].DaprdInstallPath)
app1ResourcesPath := app1Data[0]
app1ConfigFilePath := app1Data[1]
app2Data := getResourcesAndConfigFilePaths(t, config.Apps[1].DaprdInstallPath)
app2ResourcesPath := app2Data[0]
app2ConfigFilePath := app2Data[1]
// test precedence logic for resourcesPath and configPath.
err = config.resolveResourcesAndConfigFilePaths()
assert.NoError(t, err)
testcases := []struct {
name string
expectedResourcesPath string
expectedConfigFilePath string
appIndex int
}{
{
name: "resourcesPaths and configPath are resolved from dapr's default installation path.",
expectedResourcesPath: app1ResourcesPath,
expectedConfigFilePath: app1ConfigFilePath,
appIndex: 0,
},
{
name: "resourcesPaths and configPath are resolved from dapr's custom installation path.",
expectedResourcesPath: app2ResourcesPath,
expectedConfigFilePath: app2ConfigFilePath,
appIndex: 1,
},
}
for _, tc := range testcases {
t.Run(tc.name, func(t *testing.T) {
assert.Equal(t, tc.expectedResourcesPath, config.Apps[tc.appIndex].ResourcesPaths[0])
assert.Equal(t, tc.expectedConfigFilePath, config.Apps[tc.appIndex].ConfigFile)
})
}
})
t.Run("test validate run config", func(t *testing.T) {
testcases := []struct {
name string
input string
expectedErr bool
}{
{
name: "valid run config",
input: validRunFilePath,
expectedErr: false,
},
{
name: "invalid run config - empty app dir path",
input: invalidRunFilePath2,
expectedErr: true,
},
{
name: "invalid run config - invalid app dir path",
input: invalidRunFilePath1,
expectedErr: true,
},
}
for _, tc := range testcases {
t.Run(tc.name, func(t *testing.T) {
config := RunFileConfig{}
config.parseAppsConfig(tc.input)
actualErr := config.validateRunConfig(tc.input)
assert.Equal(t, tc.expectedErr, actualErr != nil)
})
}
})
t.Run("test log destination for daprd and apps", func(t *testing.T) {
config := RunFileConfig{}
apps, err := config.GetApps(runFileForLogDestination)
assert.NoError(t, err)
assert.Len(t, apps, 6)
assert.Equal(t, "file", apps[0].DaprdLogDestination.String())
assert.Equal(t, "fileAndConsole", apps[0].AppLogDestination.String())
assert.Equal(t, "fileAndConsole", apps[1].DaprdLogDestination.String())
assert.Equal(t, "fileAndConsole", apps[1].AppLogDestination.String())
assert.Equal(t, "file", apps[2].DaprdLogDestination.String())
assert.Equal(t, "file", apps[2].AppLogDestination.String())
assert.Equal(t, "console", apps[3].DaprdLogDestination.String())
assert.Equal(t, "console", apps[3].AppLogDestination.String())
assert.Equal(t, "console", apps[4].DaprdLogDestination.String())
assert.Equal(t, "file", apps[4].AppLogDestination.String())
assert.Equal(t, "file", apps[5].DaprdLogDestination.String())
assert.Equal(t, "console", apps[5].AppLogDestination.String())
})
}
func TestContainerImagePullPolicy(t *testing.T) {
testcases := []struct {
name string
runfFile string
expectedPullPolicies []string
expectedBadPolicyValue string
expectedErr bool
}{
{
name: "default value is Always",
runfFile: validRunFilePath,
expectedPullPolicies: []string{"Always", "Always"},
expectedErr: false,
},
{
name: "custom value is respected",
runfFile: runFileForContainerImagePullPolicy,
expectedPullPolicies: []string{"IfNotPresent", "Always"},
expectedErr: false,
},
{
name: "invalid value is rejected",
runfFile: runFileForContainerImagePullPolicyInvalid,
expectedPullPolicies: []string{"Always", "Always"},
expectedBadPolicyValue: "Invalid",
expectedErr: true,
},
}
for _, tc := range testcases {
t.Run(tc.name, func(t *testing.T) {
config := RunFileConfig{}
config.parseAppsConfig(tc.runfFile)
err := config.validateRunConfig(tc.runfFile)
if tc.expectedErr {
assert.Error(t, err)
assert.Contains(t, err.Error(), fmt.Sprintf("invalid containerImagePullPolicy: %s, allowed values: Always, Never, IfNotPresent", tc.expectedBadPolicyValue))
return
}
assert.Equal(t, tc.expectedPullPolicies[0], config.Apps[0].ContainerImagePullPolicy)
assert.Equal(t, tc.expectedPullPolicies[1], config.Apps[1].ContainerImagePullPolicy)
})
}
}
func TestMultiResourcePathsResolution(t *testing.T) {
config := RunFileConfig{}
err := config.parseAppsConfig(runFileForMultiResourcePaths)
assert.NoError(t, err)
err = config.validateRunConfig(runFileForMultiResourcePaths)
assert.NoError(t, err)
// test precedence logic for multiple resources paths.
err = config.resolveResourcesAndConfigFilePaths()
assert.NoError(t, err)
testcases := []struct {
name string
expectedNoOfResources int
expectedResourcesPathsContains string
appIndex int
}{
{
name: "resourcesPaths should have 2 paths",
expectedNoOfResources: 2,
expectedResourcesPathsContains: filepath.Join(config.Apps[0].AppDirPath, "resources"),
appIndex: 0,
},
{
name: "resourcesPaths should have 2 paths",
expectedNoOfResources: 2,
expectedResourcesPathsContains: filepath.Join("backend", ".dapr", "resources"),
appIndex: 0,
},
{
name: "resourcesPaths should have 2 path from common section",
expectedNoOfResources: 2,
expectedResourcesPathsContains: filepath.Join("app", "resources"),
appIndex: 1,
},
{
name: "resourcesPaths should have 1 path from .dapr's folder",
expectedNoOfResources: 1,
expectedResourcesPathsContains: filepath.Join("backend", ".dapr", "resources"),
appIndex: 2,
},
}
for _, tc := range testcases {
t.Run(tc.name, func(t *testing.T) {
assert.Len(t, config.Apps[tc.appIndex].ResourcesPaths, tc.expectedNoOfResources)
var rsrcFound bool
for _, resourcePath := range config.Apps[tc.appIndex].ResourcesPaths {
if rsrcFound = strings.Contains(resourcePath, tc.expectedResourcesPathsContains); rsrcFound {
break
}
}
assert.True(t, rsrcFound)
})
}
}
func TestGetBasePathFromAbsPath(t *testing.T) {
testcases := []struct {
name string
input string
expectedErr bool
expectedAppID string
}{
{
name: "valid absolute path",
input: filepath.Join(os.TempDir(), "test"),
expectedErr: false,
expectedAppID: "test",
},
{
name: "invalid absolute path",
input: filepath.Join("..", "test"),
expectedErr: true,
expectedAppID: "",
},
{
name: "invalid absolute path",
input: filepath.Join(".", "test"),
expectedErr: true,
expectedAppID: "",
},
}
for _, tc := range testcases {
t.Run(tc.name, func(t *testing.T) {
runFileConfig := RunFileConfig{}
appID, actualErr := runFileConfig.getBasePathFromAbsPath(tc.input)
assert.Equal(t, tc.expectedErr, actualErr != nil)
assert.Equal(t, tc.expectedAppID, appID)
})
}
}
// getResoucresAndConfigFilePaths returns a list containing resources and config file paths in order.
func getResourcesAndConfigFilePaths(t *testing.T, daprInstallPath string) []string {
t.Helper()
result := make([]string, 2)
daprDirPath, err := standalone.GetDaprRuntimePath(daprInstallPath)
assert.NoError(t, err)
result[0] = standalone.GetDaprComponentsPath(daprDirPath)
result[1] = standalone.GetDaprConfigPath(daprDirPath)
return result
}

View File

View File

View File

View File

View File

View File

@ -0,0 +1,23 @@
version: 1
common:
resourcesPath: ./app/resources
appProtocol: HTTP
appHealthProbeTimeout: 10
env:
DEBUG: false
tty: sts
apps:
- appDirPath: ./webapp/
resourcesPath: ./resources
configFilePath: ./config.yaml
appPort: 8080
appHealthProbeTimeout: 1
command: ["python3", "app.py"]
- appID: backend
appDirPath: ./backend/
appProtocol: GRPC
appPort: 3000
unixDomainSocket: /tmp/test-socket
env:
DEBUG: true
command: ["./backend"]

View File

@ -0,0 +1,24 @@
version: 1
common:
resourcesPath: ./app/resources
appProtocol: HTTP
appHealthProbeTimeout: 10
env:
DEBUG: false
tty: sts
apps:
- appDirPath: ./webapp/
resourcesPath: ./resources
configFilePath: ./config.yaml
appPort: 8080
appHealthProbeTimeout: 1
containerImagePullPolicy: IfNotPresent
containerImage: ghcr.io/dapr/dapr-workflows-python-sdk:latest
- appID: backend
appDirPath: ./backend/
appProtocol: GRPC
appPort: 3000
unixDomainSocket: /tmp/test-socket
env:
DEBUG: true
containerImage: ghcr.io/dapr/dapr-workflows-csharp-sdk:latest

View File

@ -0,0 +1,24 @@
version: 1
common:
resourcesPath: ./app/resources
appProtocol: HTTP
appHealthProbeTimeout: 10
env:
DEBUG: false
tty: sts
apps:
- appDirPath: ./webapp/
resourcesPath: ./resources
configFilePath: ./config.yaml
appPort: 8080
appHealthProbeTimeout: 1
containerImagePullPolicy: Invalid
containerImage: ghcr.io/dapr/dapr-workflows-python-sdk:latest
- appID: backend
appDirPath: ./backend/
appProtocol: GRPC
appPort: 3000
unixDomainSocket: /tmp/test-socket
env:
DEBUG: true
containerImage: ghcr.io/dapr/dapr-workflows-csharp-sdk:latest

View File

@ -0,0 +1,5 @@
version: 1
common:
apps:
- appDirPath: ./webapp/
- appID: backend

View File

@ -0,0 +1,6 @@
version: 1
common:
apps:
- appDirPath: ./webapp/
- appID: backend
appDirPath: ./invalid_backend/

View File

@ -0,0 +1,25 @@
version: 1
common:
apps:
- appDirPath: ./webapp/
appID: app_1
- appDirPath: ./webapp/
appID: app_2
daprdLogDestination: fileAndConsole
appLogDestination: fileAndConsole
- appDirPath: ./webapp/
appID: app_3
daprdLogDestination: file
appLogDestination: file
- appDirPath: ./webapp/
appID: app_4
daprdLogDestination: console
appLogDestination: console
- appDirPath: ./webapp/
appID: app_5
daprdLogDestination: console
appLogDestination: file
- appDirPath: ./webapp/
appID: app_6
daprdLogDestination: file
appLogDestination: console

View File

@ -0,0 +1,19 @@
version: 1
common:
# resourcesPath and resourcesPaths should be combined into resourcesPaths and should contain 1 path to load resources from.
resourcesPath: ./app/resources
resourcesPaths:
- ./app/resources
configFilePath: ./app/config.yaml
apps:
# resourcesPaths should contain 2 paths to load resources from.
- appDirPath: ./webapp/
resourcesPath: ./resources
resourcesPaths:
- ../backend/.dapr/resources
# resourcesPaths should be resolved from common's section and should contain 1 path to load resources from.
- appDirPath: ./webapp/
appID: webapp_1
# resourcesPaths resolved from app/.dapr folder and should contain 1 path to load resources from.
- appID: backend
appDirPath: ./backend/

View File

@ -0,0 +1,15 @@
version: 1
common:
resourcesPath: ./app/resources
configFilePath: ./app/config.yaml
apps:
# tests resourcesPath and config_file resolved from app's section.
- appDirPath: ./webapp/
resourcesPath: ./resources
configFilePath: ./config.yaml
# tests resourcesPath and config_file resolved from app/.dapr folder.
- appID: backend
appDirPath: ./backend/
# tests resourcesPath and config_file resolved from common's section.
- appID: app_common_section
appDirPath: ./app_precedence_rule/

View File

@ -0,0 +1,10 @@
version: 1
common:
apps:
# tests resourcesPath and config_file resolved from dapr's default installation directory.
- appID: app_default_dapr_dir
appDirPath: ./app_precedence_rule/
# tests resourcesPath and config_file resolved from dapr's custom installation directory.
- appID: app_custom_dapr_dir
appDirPath: ./app_precedence_rule/
runtimePath: ../custom_dapr_dir

View File

View File

View File

@ -55,10 +55,10 @@ func isStringNilOrEmpty(val *string) bool {
return val == nil || strings.TrimSpace(*val) == ""
}
func (b *bundleDetails) getPlacementImageName() string {
func (b *bundleDetails) getDaprImageName() string {
return *b.DaprImageName
}
func (b *bundleDetails) getPlacementImageFileName() string {
func (b *bundleDetails) getDaprImageFileName() string {
return *b.DaprImageFileName
}

View File

@ -44,8 +44,8 @@ func TestParseDetails(t *testing.T) {
assert.Equal(t, "0.10.0", *bd.DashboardVersion, "expected versions to match")
assert.Equal(t, "dist", *bd.BinarySubDir, "expected value to match")
assert.Equal(t, "docker", *bd.ImageSubDir, "expected value to match")
assert.Equal(t, "daprio/dapr:1.7.2", bd.getPlacementImageName(), "expected value to match")
assert.Equal(t, "daprio-dapr-1.7.2.tar.gz", bd.getPlacementImageFileName(), "expected value to match")
assert.Equal(t, "daprio/dapr:1.7.2", bd.getDaprImageName(), "expected value to match")
assert.Equal(t, "daprio-dapr-1.7.2.tar.gz", bd.getDaprImageFileName(), "expected value to match")
}
func TestParseDetailsMissingDetails(t *testing.T) {

View File

@ -17,25 +17,50 @@ import (
"os"
path_filepath "path/filepath"
"runtime"
"strings"
)
const (
defaultDaprDirName = ".dapr"
defaultDaprBinDirName = "bin"
defaultComponentsDirName = "components"
defaultConfigFileName = "config.yaml"
DefaultDaprDirName = ".dapr"
DefaultConfigFileName = "config.yaml"
DefaultResourcesDirName = "resources"
defaultDaprBinDirName = "bin"
defaultComponentsDirName = "components"
defaultSchedulerDirName = "scheduler"
defaultSchedulerDataDirName = "data"
)
func defaultDaprDirPath() string {
homeDir, _ := os.UserHomeDir()
return path_filepath.Join(homeDir, defaultDaprDirName)
// GetDaprRuntimePath returns the dapr runtime installation path.
// daprRuntimePath is based on the --runtime-path command line flag.
// The order of precedence is:
// 1. From --runtime-path command line flag appended with `.dapr`
// 2. From DAPR_RUNTIME_PATH environment variable appended with `.dapr`
// 3. default $HOME/.dapr
func GetDaprRuntimePath(daprRuntimePath string) (string, error) {
runtimePath := strings.TrimSpace(daprRuntimePath)
if runtimePath != "" {
return path_filepath.Join(runtimePath, DefaultDaprDirName), nil
}
envRuntimePath := strings.TrimSpace(os.Getenv("DAPR_RUNTIME_PATH"))
if envRuntimePath != "" {
return path_filepath.Join(envRuntimePath, DefaultDaprDirName), nil
}
homeDir, err := os.UserHomeDir()
if err != nil {
return "", err
}
return path_filepath.Join(homeDir, DefaultDaprDirName), nil
}
func defaultDaprBinPath() string {
return path_filepath.Join(defaultDaprDirPath(), defaultDaprBinDirName)
func getDaprBinPath(daprDir string) string {
return path_filepath.Join(daprDir, defaultDaprBinDirName)
}
func binaryFilePath(binaryDir string, binaryFilePrefix string) string {
func binaryFilePathWithDir(binaryDir string, binaryFilePrefix string) string {
binaryPath := path_filepath.Join(binaryDir, binaryFilePrefix)
if runtime.GOOS == daprWindowsOS {
binaryPath += ".exe"
@ -43,10 +68,19 @@ func binaryFilePath(binaryDir string, binaryFilePrefix string) string {
return binaryPath
}
func DefaultComponentsDirPath() string {
return path_filepath.Join(defaultDaprDirPath(), defaultComponentsDirName)
func lookupBinaryFilePath(inputInstallPath string, binaryFilePrefix string) (string, error) {
daprPath, err := GetDaprRuntimePath(inputInstallPath)
if err != nil {
return "", err
}
return binaryFilePathWithDir(getDaprBinPath(daprPath), binaryFilePrefix), nil
}
func DefaultConfigFilePath() string {
return path_filepath.Join(defaultDaprDirPath(), defaultConfigFileName)
func GetDaprComponentsPath(daprDir string) string {
return path_filepath.Join(daprDir, defaultComponentsDirName)
}
func GetDaprConfigPath(daprDir string) string {
return path_filepath.Join(daprDir, DefaultConfigFileName)
}

Some files were not shown because too many files have changed in this diff Show More