diff --git a/.changelog/10914.txt b/.changelog/10914.txt
new file mode 100644
index 0000000000..67aadc4f3c
--- /dev/null
+++ b/.changelog/10914.txt
@@ -0,0 +1,3 @@
+```release-note:bug
+ui: hide create button for policies/roles/namespace if users token has no write permissions to those areas
+```
diff --git a/.changelog/11129.txt b/.changelog/11129.txt
new file mode 100644
index 0000000000..9d1d65a8bb
--- /dev/null
+++ b/.changelog/11129.txt
@@ -0,0 +1,4 @@
+```release-note:improvement
+ui: Add initial support for partitions to intentions
+```
+
diff --git a/.changelog/11130.txt b/.changelog/11130.txt
new file mode 100644
index 0000000000..4a872c7fc0
--- /dev/null
+++ b/.changelog/11130.txt
@@ -0,0 +1,4 @@
+```release-note:improvement
+ui: Removed informational panel from the namespace selector menu when editing
+namespaces
+```
diff --git a/.changelog/11149.txt b/.changelog/11149.txt
new file mode 100644
index 0000000000..b028e0ac74
--- /dev/null
+++ b/.changelog/11149.txt
@@ -0,0 +1,3 @@
+```release-note:bug
+ui: Don't show a CRD warning for read-only intentions
+```
diff --git a/CHANGELOG.md b/CHANGELOG.md
index 837fd85acd..60011bf4c5 100644
--- a/CHANGELOG.md
+++ b/CHANGELOG.md
@@ -47,6 +47,34 @@ manage licenses on older servers [[GH-10952](https://github.com/hashicorp/consul
* use the MaxQueryTime instead of RPCHoldTimeout for blocking RPC queries
[[GH-8978](https://github.com/hashicorp/consul/pull/8978)]. [[GH-10299](https://github.com/hashicorp/consul/issues/10299)]
+## 1.10.3 (September 27, 2021)
+
+FEATURES:
+
+* sso/oidc: **(Enterprise only)** Add support for providing acr_values in OIDC auth flow [[GH-11026](https://github.com/hashicorp/consul/issues/11026)]
+
+IMPROVEMENTS:
+
+* audit-logging: **(Enterprise Only)** Audit logs will now include select HTTP headers in each logs payload. Those headers are: `Forwarded`, `Via`, `X-Forwarded-For`, `X-Forwarded-Host` and `X-Forwarded-Proto`. [[GH-11107](https://github.com/hashicorp/consul/issues/11107)]
+* connect: update supported envoy versions to 1.18.4, 1.17.4, 1.16.5 [[GH-10961](https://github.com/hashicorp/consul/issues/10961)]
+* telemetry: Add new metrics for the count of KV entries in the Consul store. [[GH-11090](https://github.com/hashicorp/consul/issues/11090)]
+
+BUG FIXES:
+
+* api: Revert early out errors from license APIs to allow v1.10+ clients to
+manage licenses on older servers [[GH-10952](https://github.com/hashicorp/consul/issues/10952)]
+* connect: Fix upstream listener escape hatch for prepared queries [[GH-11109](https://github.com/hashicorp/consul/issues/11109)]
+* grpc: strip local ACL tokens from RPCs during forwarding if crossing datacenters [[GH-11099](https://github.com/hashicorp/consul/issues/11099)]
+* tls: consider presented intermediates during server connection tls handshake. [[GH-10964](https://github.com/hashicorp/consul/issues/10964)]
+* ui: **(Enterprise Only)** Fix saving intentions with namespaced source/destination [[GH-11095](https://github.com/hashicorp/consul/issues/11095)]
+* ui: Don't show a CRD warning for read-only intentions [[GH-11149](https://github.com/hashicorp/consul/issues/11149)]
+* ui: Ensure routing-config page blocking queries are cleaned up correctly [[GH-10915](https://github.com/hashicorp/consul/issues/10915)]
+* ui: Ignore reported permissions for KV area meaning the KV is always enabled
+for both read/write access if the HTTP API allows. [[GH-10916](https://github.com/hashicorp/consul/issues/10916)]
+* ui: hide create button for policies/roles/namespace if users token has no write permissions to those areas [[GH-10914](https://github.com/hashicorp/consul/issues/10914)]
+* xds: ensure the active streams counters are 64 bit aligned on 32 bit systems [[GH-11085](https://github.com/hashicorp/consul/issues/11085)]
+* xds: fixed a bug where Envoy sidecars could enter a state where they failed to receive xds updates from Consul [[GH-10987](https://github.com/hashicorp/consul/issues/10987)]
+
## 1.10.2 (August 27, 2021)
KNOWN ISSUES:
@@ -249,6 +277,23 @@ NOTES:
* legal: **(Enterprise only)** Enterprise binary downloads will now include a copy of the EULA and Terms of Evaluation in the zip archive
+## 1.9.10 (September 27, 2021)
+
+FEATURES:
+
+* sso/oidc: **(Enterprise only)** Add support for providing acr_values in OIDC auth flow [[GH-11026](https://github.com/hashicorp/consul/issues/11026)]
+
+IMPROVEMENTS:
+
+* audit-logging: **(Enterprise Only)** Audit logs will now include select HTTP headers in each logs payload. Those headers are: `Forwarded`, `Via`, `X-Forwarded-For`, `X-Forwarded-Host` and `X-Forwarded-Proto`. [[GH-11107](https://github.com/hashicorp/consul/issues/11107)]
+* connect: update supported envoy versions to 1.16.5 [[GH-10961](https://github.com/hashicorp/consul/issues/10961)]
+* telemetry: Add new metrics for the count of KV entries in the Consul store. [[GH-11090](https://github.com/hashicorp/consul/issues/11090)]
+
+BUG FIXES:
+
+* tls: consider presented intermediates during server connection tls handshake. [[GH-10964](https://github.com/hashicorp/consul/issues/10964)]
+* ui: **(Enterprise Only)** Fix saving intentions with namespaced source/destination [[GH-11095](https://github.com/hashicorp/consul/issues/11095)]
+
## 1.9.9 (August 27, 2021)
KNOWN ISSUES:
@@ -590,6 +635,21 @@ BUG FIXES:
* telemetry: fixed a bug that caused logs to be flooded with `[WARN] agent.router: Non-server in server-only area` [[GH-8685](https://github.com/hashicorp/consul/issues/8685)]
* ui: show correct datacenter for gateways [[GH-8704](https://github.com/hashicorp/consul/issues/8704)]
+## 1.8.16 (September 27, 2021)
+
+FEATURES:
+
+* sso/oidc: **(Enterprise only)** Add support for providing acr_values in OIDC auth flow [[GH-11026](https://github.com/hashicorp/consul/issues/11026)]
+
+IMPROVEMENTS:
+
+* audit-logging: **(Enterprise Only)** Audit logs will now include select HTTP headers in each logs payload. Those headers are: `Forwarded`, `Via`, `X-Forwarded-For`, `X-Forwarded-Host` and `X-Forwarded-Proto`. [[GH-11107](https://github.com/hashicorp/consul/issues/11107)]
+
+BUG FIXES:
+
+* tls: consider presented intermediates during server connection tls handshake. [[GH-10964](https://github.com/hashicorp/consul/issues/10964)]
+* ui: **(Enterprise Only)** Fixes a visual issue where namespaces would "double up" in the Source/Destination select menu when creating/editing intentions [[GH-11102](https://github.com/hashicorp/consul/issues/11102)]
+
## 1.8.15 (August 27, 2021)
KNOWN ISSUES:
diff --git a/agent/agent.go b/agent/agent.go
index 1fdea4bc6e..a143ff94de 100644
--- a/agent/agent.go
+++ b/agent/agent.go
@@ -2864,44 +2864,6 @@ func (a *Agent) AdvertiseAddrLAN() string {
return a.config.AdvertiseAddrLAN.String()
}
-// resolveProxyCheckAddress returns the best address to use for a TCP check of
-// the proxy's public listener. It expects the input to already have default
-// values populated by applyProxyConfigDefaults. It may return an empty string
-// indicating that the TCP check should not be created at all.
-//
-// By default this uses the proxy's bind address which in turn defaults to the
-// agent's bind address. If the proxy bind address ends up being 0.0.0.0 we have
-// to assume the agent can dial it over loopback which is usually true.
-//
-// In some topologies such as proxy being in a different container, the IP the
-// agent used to dial proxy over a local bridge might not be the same as the
-// container's public routable IP address so we allow a manual override of the
-// check address in config "tcp_check_address" too.
-//
-// Finally the TCP check can be disabled by another manual override
-// "disable_tcp_check" in cases where the agent will never be able to dial the
-// proxy directly for some reason.
-func (a *Agent) resolveProxyCheckAddress(proxyCfg map[string]interface{}) string {
- // If user disabled the check return empty string
- if disable, ok := proxyCfg["disable_tcp_check"].(bool); ok && disable {
- return ""
- }
-
- // If user specified a custom one, use that
- if chkAddr, ok := proxyCfg["tcp_check_address"].(string); ok && chkAddr != "" {
- return chkAddr
- }
-
- // If we have a bind address and its diallable, use that
- if bindAddr, ok := proxyCfg["bind_address"].(string); ok &&
- bindAddr != "" && bindAddr != "0.0.0.0" && bindAddr != "[::]" {
- return bindAddr
- }
-
- // Default to localhost
- return "127.0.0.1"
-}
-
func (a *Agent) cancelCheckMonitors(checkID structs.CheckID) {
// Stop any monitors
delete(a.checkReapAfter, checkID)
diff --git a/agent/consul/autopilot.go b/agent/consul/autopilot.go
index d926e4a991..5033032c84 100644
--- a/agent/consul/autopilot.go
+++ b/agent/consul/autopilot.go
@@ -58,7 +58,7 @@ func (d *AutopilotDelegate) NotifyState(state *autopilot.State) {
func (d *AutopilotDelegate) RemoveFailedServer(srv *autopilot.Server) {
go func() {
if err := d.server.RemoveFailedNode(srv.Name, false); err != nil {
- d.server.logger.Error("failedto remove server", "name", srv.Name, "id", srv.ID, "error", err)
+ d.server.logger.Error("failed to remove server", "name", srv.Name, "id", srv.ID, "error", err)
}
}()
}
diff --git a/agent/consul/intention_endpoint_test.go b/agent/consul/intention_endpoint_test.go
index 7ddf7d9d6c..64bb466f97 100644
--- a/agent/consul/intention_endpoint_test.go
+++ b/agent/consul/intention_endpoint_test.go
@@ -75,7 +75,7 @@ func TestIntentionApply_new(t *testing.T) {
//nolint:staticcheck
ixn.Intention.UpdatePrecedence()
// Partition fields will be normalized on Intention.Get
- ixn.Intention.NormalizePartitionFields()
+ ixn.Intention.FillPartitionAndNamespace(nil, true)
require.Equal(t, ixn.Intention, actual)
}
@@ -269,7 +269,7 @@ func TestIntentionApply_updateGood(t *testing.T) {
//nolint:staticcheck
ixn.Intention.UpdatePrecedence()
// Partition fields will be normalized on Intention.Get
- ixn.Intention.NormalizePartitionFields()
+ ixn.Intention.FillPartitionAndNamespace(nil, true)
require.Equal(t, ixn.Intention, actual)
}
}
diff --git a/agent/consul/state/acl.go b/agent/consul/state/acl.go
index 8023b95faf..548bb7c957 100644
--- a/agent/consul/state/acl.go
+++ b/agent/consul/state/acl.go
@@ -1741,3 +1741,51 @@ func intFromBool(cond bool) byte {
}
return 0
}
+
+func aclPolicyInsert(tx WriteTxn, policy *structs.ACLPolicy) error {
+ if err := tx.Insert(tableACLPolicies, policy); err != nil {
+ return fmt.Errorf("failed inserting acl policy: %v", err)
+ }
+ return updateTableIndexEntries(tx, tableACLPolicies, policy.ModifyIndex, &policy.EnterpriseMeta)
+}
+
+func aclRoleInsert(tx WriteTxn, role *structs.ACLRole) error {
+ // insert the role into memdb
+ if err := tx.Insert(tableACLRoles, role); err != nil {
+ return fmt.Errorf("failed inserting acl role: %v", err)
+ }
+
+ // update acl-roles index
+ return updateTableIndexEntries(tx, tableACLRoles, role.ModifyIndex, &role.EnterpriseMeta)
+}
+
+func aclTokenInsert(tx WriteTxn, token *structs.ACLToken) error {
+ // insert the token into memdb
+ if err := tx.Insert(tableACLTokens, token); err != nil {
+ return fmt.Errorf("failed inserting acl token: %v", err)
+ }
+ // update the overall acl-tokens index
+ return updateTableIndexEntries(tx, tableACLTokens, token.ModifyIndex, token.EnterpriseMetadata())
+}
+
+func aclAuthMethodInsert(tx WriteTxn, method *structs.ACLAuthMethod) error {
+ // insert the auth method into memdb
+ if err := tx.Insert(tableACLAuthMethods, method); err != nil {
+ return fmt.Errorf("failed inserting acl role: %v", err)
+ }
+
+ // update acl-auth-methods index
+ return updateTableIndexEntries(tx, tableACLAuthMethods, method.ModifyIndex, &method.EnterpriseMeta)
+}
+
+func aclBindingRuleInsert(tx WriteTxn, rule *structs.ACLBindingRule) error {
+ rule.EnterpriseMeta.Normalize()
+
+ // insert the role into memdb
+ if err := tx.Insert(tableACLBindingRules, rule); err != nil {
+ return fmt.Errorf("failed inserting acl role: %v", err)
+ }
+
+ // update acl-binding-rules index
+ return updateTableIndexEntries(tx, tableACLBindingRules, rule.ModifyIndex, &rule.EnterpriseMeta)
+}
diff --git a/agent/consul/state/acl_oss.go b/agent/consul/state/acl_oss.go
index fced3749d4..25483fa3e1 100644
--- a/agent/consul/state/acl_oss.go
+++ b/agent/consul/state/acl_oss.go
@@ -11,15 +11,10 @@ import (
"github.com/hashicorp/consul/agent/structs"
)
-func aclPolicyInsert(tx WriteTxn, policy *structs.ACLPolicy) error {
- if err := tx.Insert(tableACLPolicies, policy); err != nil {
- return fmt.Errorf("failed inserting acl policy: %v", err)
+func updateTableIndexEntries(tx WriteTxn, tableName string, modifyIndex uint64, _ *structs.EnterpriseMeta) error {
+ if err := indexUpdateMaxTxn(tx, modifyIndex, tableName); err != nil {
+ return fmt.Errorf("failed updating %s index: %v", tableName, err)
}
-
- if err := indexUpdateMaxTxn(tx, policy.ModifyIndex, tableACLPolicies); err != nil {
- return fmt.Errorf("failed updating acl policies index: %v", err)
- }
-
return nil
}
@@ -56,20 +51,6 @@ func (s *Store) ACLPolicyUpsertValidateEnterprise(*structs.ACLPolicy, *structs.A
///// ACL Token Functions /////
///////////////////////////////////////////////////////////////////////////////
-func aclTokenInsert(tx WriteTxn, token *structs.ACLToken) error {
- // insert the token into memdb
- if err := tx.Insert(tableACLTokens, token); err != nil {
- return fmt.Errorf("failed inserting acl token: %v", err)
- }
-
- // update the overall acl-tokens index
- if err := indexUpdateMaxTxn(tx, token.ModifyIndex, tableACLTokens); err != nil {
- return fmt.Errorf("failed updating acl tokens index: %v", err)
- }
-
- return nil
-}
-
func aclTokenGetFromIndex(tx ReadTxn, id string, index string, entMeta *structs.EnterpriseMeta) (<-chan struct{}, interface{}, error) {
return tx.FirstWatch(tableACLTokens, index, id)
}
@@ -119,19 +100,6 @@ func (s *Store) ACLTokenUpsertValidateEnterprise(token *structs.ACLToken, existi
///// ACL Role Functions /////
///////////////////////////////////////////////////////////////////////////////
-func aclRoleInsert(tx WriteTxn, role *structs.ACLRole) error {
- // insert the role into memdb
- if err := tx.Insert(tableACLRoles, role); err != nil {
- return fmt.Errorf("failed inserting acl role: %v", err)
- }
-
- // update the overall acl-roles index
- if err := indexUpdateMaxTxn(tx, role.ModifyIndex, tableACLRoles); err != nil {
- return fmt.Errorf("failed updating acl roles index: %v", err)
- }
- return nil
-}
-
func aclRoleGetByID(tx ReadTxn, id string, _ *structs.EnterpriseMeta) (<-chan struct{}, interface{}, error) {
return tx.FirstWatch(tableACLRoles, indexID, id)
}
@@ -165,20 +133,6 @@ func (s *Store) ACLRoleUpsertValidateEnterprise(role *structs.ACLRole, existing
///// ACL Binding Rule Functions /////
///////////////////////////////////////////////////////////////////////////////
-func aclBindingRuleInsert(tx WriteTxn, rule *structs.ACLBindingRule) error {
- // insert the role into memdb
- if err := tx.Insert(tableACLBindingRules, rule); err != nil {
- return fmt.Errorf("failed inserting acl role: %v", err)
- }
-
- // update the overall acl-binding-rules index
- if err := indexUpdateMaxTxn(tx, rule.ModifyIndex, tableACLBindingRules); err != nil {
- return fmt.Errorf("failed updating acl binding-rules index: %v", err)
- }
-
- return nil
-}
-
func aclBindingRuleGetByID(tx ReadTxn, id string, _ *structs.EnterpriseMeta) (<-chan struct{}, interface{}, error) {
return tx.FirstWatch(tableACLBindingRules, indexID, id)
}
@@ -220,20 +174,6 @@ func (s *Store) ACLBindingRuleUpsertValidateEnterprise(rule *structs.ACLBindingR
///// ACL Auth Method Functions /////
///////////////////////////////////////////////////////////////////////////////
-func aclAuthMethodInsert(tx WriteTxn, method *structs.ACLAuthMethod) error {
- // insert the role into memdb
- if err := tx.Insert(tableACLAuthMethods, method); err != nil {
- return fmt.Errorf("failed inserting acl role: %v", err)
- }
-
- // update the overall acl-auth-methods index
- if err := indexUpdateMaxTxn(tx, method.ModifyIndex, tableACLAuthMethods); err != nil {
- return fmt.Errorf("failed updating acl auth methods index: %v", err)
- }
-
- return nil
-}
-
func aclAuthMethodGetByName(tx ReadTxn, method string, _ *structs.EnterpriseMeta) (<-chan struct{}, interface{}, error) {
return tx.FirstWatch(tableACLAuthMethods, indexID, Query{Value: method})
}
diff --git a/agent/consul/state/intention_test.go b/agent/consul/state/intention_test.go
index 7ddd4c5a9a..f2a5f87867 100644
--- a/agent/consul/state/intention_test.go
+++ b/agent/consul/state/intention_test.go
@@ -156,7 +156,7 @@ func TestStore_IntentionSetGet_basic(t *testing.T) {
//nolint:staticcheck
expected.SetHash()
- expected.NormalizePartitionFields()
+ expected.FillPartitionAndNamespace(nil, true)
}
require.True(t, watchFired(ws), "watch fired")
@@ -1098,7 +1098,7 @@ func TestStore_IntentionsList(t *testing.T) {
UpdatedAt: testTimeA,
}
if !legacy {
- ret.NormalizePartitionFields()
+ ret.FillPartitionAndNamespace(nil, true)
}
return ret
}
diff --git a/agent/structs/intention_oss.go b/agent/structs/intention_oss.go
index 274f799d65..0c445b0a89 100644
--- a/agent/structs/intention_oss.go
+++ b/agent/structs/intention_oss.go
@@ -74,8 +74,3 @@ func (ixn *Intention) FillPartitionAndNamespace(entMeta *EnterpriseMeta, fillDef
ixn.SourcePartition = ""
ixn.DestinationPartition = ""
}
-
-func (ixn *Intention) NormalizePartitionFields() {
- ixn.SourcePartition = ""
- ixn.DestinationPartition = ""
-}
diff --git a/agent/structs/testing_intention.go b/agent/structs/testing_intention.go
index 3497ba2fcd..c8a42d7916 100644
--- a/agent/structs/testing_intention.go
+++ b/agent/structs/testing_intention.go
@@ -15,6 +15,6 @@ func TestIntention(t testing.T) *Intention {
SourceType: IntentionSourceConsul,
Meta: map[string]string{},
}
- ixn.NormalizePartitionFields()
+ ixn.FillPartitionAndNamespace(nil, true)
return ixn
}
diff --git a/command/acl/acl_helpers.go b/command/acl/acl_helpers.go
index 296a6b9f90..add5c930c5 100644
--- a/command/acl/acl_helpers.go
+++ b/command/acl/acl_helpers.go
@@ -71,23 +71,26 @@ func GetPolicyIDFromPartial(client *api.Client, partialID string) (string, error
return policyID, nil
}
-func GetPolicyIDByName(client *api.Client, name string) (string, error) {
+func GetPolicyByName(client *api.Client, name string) (*api.ACLPolicy, error) {
if name == "" {
- return "", fmt.Errorf("No name specified")
+ return nil, fmt.Errorf("No name specified")
}
- policies, _, err := client.ACL().PolicyList(nil)
+ policy, _, err := client.ACL().PolicyReadByName(name, nil)
+ if err != nil {
+ return nil, fmt.Errorf("Failed to find policy with name %s: %w", name, err)
+ }
+
+ return policy, nil
+}
+
+func GetPolicyIDByName(client *api.Client, name string) (string, error) {
+ policy, err := GetPolicyByName(client, name)
if err != nil {
return "", err
}
- for _, policy := range policies {
- if policy.Name == name {
- return policy.ID, nil
- }
- }
-
- return "", fmt.Errorf("No such policy with name %s", name)
+ return policy.ID, nil
}
func GetRulesFromLegacyToken(client *api.Client, tokenID string, isSecret bool) (string, error) {
diff --git a/command/acl/policy/read/policy_read.go b/command/acl/policy/read/policy_read.go
index 3d043815f6..c5be7f63b4 100644
--- a/command/acl/policy/read/policy_read.go
+++ b/command/acl/policy/read/policy_read.go
@@ -5,6 +5,7 @@ import (
"fmt"
"strings"
+ "github.com/hashicorp/consul/api"
"github.com/hashicorp/consul/command/acl"
"github.com/hashicorp/consul/command/acl/policy"
"github.com/hashicorp/consul/command/flags"
@@ -67,19 +68,26 @@ func (c *cmd) Run(args []string) int {
}
var policyID string
+ var pol *api.ACLPolicy
if c.policyID != "" {
policyID, err = acl.GetPolicyIDFromPartial(client, c.policyID)
+ if err != nil {
+ c.UI.Error(fmt.Sprintf("Error determining policy ID: %v", err))
+ return 1
+ }
+ pol, _, err = client.ACL().PolicyRead(policyID, nil)
} else {
- policyID, err = acl.GetPolicyIDByName(client, c.policyName)
- }
- if err != nil {
- c.UI.Error(fmt.Sprintf("Error determining policy ID: %v", err))
- return 1
+ pol, err = acl.GetPolicyByName(client, c.policyName)
}
- p, _, err := client.ACL().PolicyRead(policyID, nil)
if err != nil {
- c.UI.Error(fmt.Sprintf("Error reading policy %q: %v", policyID, err))
+ var errArg string
+ if c.policyID != "" {
+ errArg = fmt.Sprintf("id:%s", policyID)
+ } else {
+ errArg = fmt.Sprintf("name:%s", c.policyName)
+ }
+ c.UI.Error(fmt.Sprintf("Error reading policy %q: %v", errArg, err))
return 1
}
@@ -88,7 +96,7 @@ func (c *cmd) Run(args []string) int {
c.UI.Error(err.Error())
return 1
}
- out, err := formatter.FormatPolicy(p)
+ out, err := formatter.FormatPolicy(pol)
if err != nil {
c.UI.Error(err.Error())
return 1
diff --git a/command/acl/policy/read/policy_read_test.go b/command/acl/policy/read/policy_read_test.go
index 377a75ab23..b365287194 100644
--- a/command/acl/policy/read/policy_read_test.go
+++ b/command/acl/policy/read/policy_read_test.go
@@ -53,6 +53,7 @@ func TestPolicyReadCommand(t *testing.T) {
)
assert.NoError(err)
+ // Test querying by id field
args := []string{
"-http-addr=" + a.HTTPAddr(),
"-token=root",
@@ -66,6 +67,22 @@ func TestPolicyReadCommand(t *testing.T) {
output := ui.OutputWriter.String()
assert.Contains(output, fmt.Sprintf("test-policy"))
assert.Contains(output, policy.ID)
+
+ // Test querying by name field
+ argsName := []string{
+ "-http-addr=" + a.HTTPAddr(),
+ "-token=root",
+ "-name=test-policy",
+ }
+
+ cmd = New(ui)
+ code = cmd.Run(argsName)
+ assert.Equal(code, 0)
+ assert.Empty(ui.ErrorWriter.String())
+
+ output = ui.OutputWriter.String()
+ assert.Contains(output, fmt.Sprintf("test-policy"))
+ assert.Contains(output, policy.ID)
}
func TestPolicyReadCommand_JSON(t *testing.T) {
diff --git a/ui/packages/consul-ui/app/abilities/intention.js b/ui/packages/consul-ui/app/abilities/intention.js
index 35551e670a..91f3a013b4 100644
--- a/ui/packages/consul-ui/app/abilities/intention.js
+++ b/ui/packages/consul-ui/app/abilities/intention.js
@@ -4,6 +4,9 @@ export default class IntentionAbility extends BaseAbility {
resource = 'intention';
get canWrite() {
- return super.canWrite && (typeof this.item === 'undefined' || this.item.IsEditable);
+ return super.canWrite && (typeof this.item === 'undefined' || !this.canViewCRD);
+ }
+ get canViewCRD() {
+ return (typeof this.item !== 'undefined' && this.item.IsManagedByCRD);
}
}
diff --git a/ui/packages/consul-ui/app/adapters/intention.js b/ui/packages/consul-ui/app/adapters/intention.js
index 6bd10fbaa7..13108e860c 100644
--- a/ui/packages/consul-ui/app/adapters/intention.js
+++ b/ui/packages/consul-ui/app/adapters/intention.js
@@ -7,10 +7,11 @@ import { get } from '@ember/object';
// will give us all the intentions that have the `ns` as either the SourceNS or
// the DestinationNS.
// We currently list intentions by the * wildcard namespace for back compat reasons
+// FIXME: Is now a good time to change this behaviour ^ ?
// TODO: Update to use this.formatDatacenter()
export default class IntentionAdapter extends Adapter {
- requestForQuery(request, { dc, ns, filter, index, uri }) {
+ requestForQuery(request, { dc, ns, partition, filter, index, uri }) {
return request`
GET /v1/connect/intentions?${{ dc }}
X-Request-ID: ${uri}${
@@ -21,7 +22,7 @@ export default class IntentionAdapter extends Adapter {
}
${{
- partition: '',
+ partition: '*',
ns: '*',
index,
filter,
@@ -36,14 +37,21 @@ export default class IntentionAdapter extends Adapter {
// get the information we need from the id, which has been previously
// encoded
- const [SourceNS, SourceName, DestinationNS, DestinationName] = id
- .split(':')
- .map(decodeURIComponent);
+ const [
+ SourcePartition,
+ SourceNS,
+ SourceName,
+ DestinationPartition,
+ DestinationNS,
+ DestinationName,
+ ] = id.split(':').map(decodeURIComponent);
+ // FIXME: Service and Namespace are encoded into the URL here
+ // guessing we need to do the same thing for Partitions
return request`
GET /v1/connect/intentions/exact?${{
- source: `${SourceNS}/${SourceName}`,
- destination: `${DestinationNS}/${DestinationName}`,
+ source: `${SourcePartition}/${SourceNS}/${SourceName}`,
+ destination: `${DestinationPartition}/${DestinationNS}/${DestinationName}`,
dc: dc,
}}
Cache-Control: no-store
@@ -54,10 +62,12 @@ export default class IntentionAdapter extends Adapter {
requestForCreateRecord(request, serialized, data) {
const body = {
- SourceNS: serialized.SourceNS,
- DestinationNS: serialized.DestinationNS,
SourceName: serialized.SourceName,
DestinationName: serialized.DestinationName,
+ SourceNS: serialized.SourceNS,
+ DestinationNS: serialized.DestinationNS,
+ SourcePartition: serialized.SourcePartition,
+ DestinationPartition: serialized.DestinationPartition,
SourceType: serialized.SourceType,
Meta: serialized.Meta,
Description: serialized.Description,
@@ -72,10 +82,12 @@ export default class IntentionAdapter extends Adapter {
body.Permissions = serialized.Permissions;
}
}
+ // FIXME: Service and Namespace are encoded into the URL here
+ // guessing we need to do the same thing for Partitions
return request`
PUT /v1/connect/intentions/exact?${{
- source: `${data.SourceNS}/${data.SourceName}`,
- destination: `${data.DestinationNS}/${data.DestinationName}`,
+ source: `${data.SourcePartition}/${data.SourceNS}/${data.SourceName}`,
+ destination: `${data.DestinationPartition}/${data.DestinationNS}/${data.DestinationName}`,
dc: data.Datacenter,
}}
@@ -85,16 +97,20 @@ export default class IntentionAdapter extends Adapter {
requestForUpdateRecord(request, serialized, data) {
// you can no longer save Destinations
- delete serialized.DestinationNS;
delete serialized.DestinationName;
+ delete serialized.DestinationNS;
+ // FIXME: Does the above comment stand for partitions also?
+ delete serialized.DestinationPartition;
return this.requestForCreateRecord(...arguments);
}
requestForDeleteRecord(request, serialized, data) {
+ // FIXME: Service and Namespace are encoded into the URL here
+ // guessing we need to do the same thing for Partitions
return request`
DELETE /v1/connect/intentions/exact?${{
- source: `${data.SourceNS}/${data.SourceName}`,
- destination: `${data.DestinationNS}/${data.DestinationName}`,
+ source: `${data.SourcePartition}/${data.SourceNS}/${data.SourceName}`,
+ destination: `${data.DestinationPartition}/${data.DestinationNS}/${data.DestinationName}`,
dc: data.Datacenter,
}}
`;
diff --git a/ui/packages/consul-ui/app/components/consul/intention/form/fieldsets/index.hbs b/ui/packages/consul-ui/app/components/consul/intention/form/fieldsets/index.hbs
index e19be3d500..4d9dd03065 100644
--- a/ui/packages/consul-ui/app/components/consul/intention/form/fieldsets/index.hbs
+++ b/ui/packages/consul-ui/app/components/consul/intention/form/fieldsets/index.hbs
@@ -28,7 +28,7 @@
Search for an existing service, or enter any Service name.
{{/if}}
- {{#if (env 'CONSUL_NSPACES_ENABLED')}}
+ {{#if (can 'choose nspaces')}}
-{{/if}}
+ {{/if}}
+ {{#if (can 'choose partitions')}}
+
+ {{/if}}