Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
57 changes: 57 additions & 0 deletions docs/serving-api.md
Original file line number Diff line number Diff line change
Expand Up @@ -2110,6 +2110,20 @@ Service.</p>
Knative Routes, and by Kubernetes Services.</p>
</td>
</tr>
<tr>
<td>
<code>tls</code><br/>
<em>
<a href="#serving.knative.dev/v1alpha1.SecretTLS">
SecretTLS
</a>
</em>
</td>
<td>
<em>(Optional)</em>
<p>TLS allows the DomainMapping to terminate TLS traffic with an existing secret.</p>
</td>
</tr>
</table>
</td>
</tr>
Expand Down Expand Up @@ -2200,6 +2214,20 @@ Service.</p>
Knative Routes, and by Kubernetes Services.</p>
</td>
</tr>
<tr>
<td>
<code>tls</code><br/>
<em>
<a href="#serving.knative.dev/v1alpha1.SecretTLS">
SecretTLS
</a>
</em>
</td>
<td>
<em>(Optional)</em>
<p>TLS allows the DomainMapping to terminate TLS traffic with an existing secret.</p>
</td>
</tr>
</tbody>
</table>
<h3 id="serving.knative.dev/v1alpha1.DomainMappingStatus">DomainMappingStatus
Expand Down Expand Up @@ -2263,6 +2291,35 @@ knative.dev/pkg/apis/duck/v1.Addressable
</tr>
</tbody>
</table>
<h3 id="serving.knative.dev/v1alpha1.SecretTLS">SecretTLS
</h3>
<p>
(<em>Appears on:</em><a href="#serving.knative.dev/v1alpha1.DomainMappingSpec">DomainMappingSpec</a>)
</p>
<p>
<p>SecretTLS wrapper for TLS SecretName.</p>
</p>
<table>
<thead>
<tr>
<th>Field</th>
<th>Description</th>
</tr>
</thead>
<tbody>
<tr>
<td>
<code>secretName</code><br/>
<em>
string
</em>
</td>
<td>
<p>SecretName is the name of the existing secret used to terminate TLS traffic.</p>
</td>
</tr>
</tbody>
</table>
<hr/>
<p><em>
Generated with <code>gen-crd-api-reference-docs</code>
Expand Down
8 changes: 8 additions & 0 deletions pkg/apis/serving/v1alpha1/domainmapping_lifecycle.go
Original file line number Diff line number Diff line change
Expand Up @@ -63,6 +63,9 @@ const (
// DomainMappingConditionCertificateProvisioned condition when it is set to True
// because AutoTLS was not enabled.
AutoTLSNotEnabledMessage = "autoTLS is not enabled"
// TLSCertificateProvidedExternally indicates that a TLS secret won't be created or managed
// instead a reference to an existing TLS secret should have been provided in the DomainMapping spec
TLSCertificateProvidedExternally = "TLS certificate was provided externally"
)

// MarkTLSNotEnabled sets DomainMappingConditionCertificateProvisioned to true when
Expand All @@ -72,6 +75,11 @@ func (dms *DomainMappingStatus) MarkTLSNotEnabled(msg string) {
"TLSNotEnabled", msg)
}

func (dms *DomainMappingStatus) MarkCertificateNotRequired(msg string) {
domainMappingCondSet.Manage(dms).MarkTrueWithReason(DomainMappingConditionCertificateProvisioned,
"CertificateExternallyProvided", msg)
}

// MarkCertificateReady marks the DomainMappingConditionCertificateProvisioned
// condition to indicate that the Certificate is ready.
func (dms *DomainMappingStatus) MarkCertificateReady(name string) {
Expand Down
10 changes: 10 additions & 0 deletions pkg/apis/serving/v1alpha1/domainmapping_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -70,6 +70,12 @@ type DomainMappingList struct {
Items []DomainMapping `json:"items"`
}

// SecretTLS wrapper for TLS SecretName.
type SecretTLS struct {
// SecretName is the name of the existing secret used to terminate TLS traffic.
SecretName string `json:"secretName"`
}

// DomainMappingSpec describes the DomainMapping the user wishes to exist.
type DomainMappingSpec struct {
// Ref specifies the target of the Domain Mapping.
Expand All @@ -82,6 +88,10 @@ type DomainMappingSpec struct {
// This contract is satisfied by Knative types such as Knative Services and
// Knative Routes, and by Kubernetes Services.
Ref duckv1.KReference `json:"ref"`

// TLS allows the DomainMapping to terminate TLS traffic with an existing secret.
// +optional
TLS *SecretTLS `json:"tls,omitempty"`
}

// DomainMappingStatus describes the current state of the DomainMapping.
Expand Down
23 changes: 22 additions & 1 deletion pkg/apis/serving/v1alpha1/zz_generated.deepcopy.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

10 changes: 10 additions & 0 deletions pkg/reconciler/domainmapping/reconciler.go
Original file line number Diff line number Diff line change
Expand Up @@ -199,6 +199,16 @@ func certClass(ctx context.Context) string {
}

func (r *Reconciler) tls(ctx context.Context, dm *v1alpha1.DomainMapping) ([]netv1alpha1.IngressTLS, []netv1alpha1.HTTP01Challenge, error) {
if dm.Spec.TLS != nil {
dm.Status.MarkCertificateNotRequired(v1alpha1.TLSCertificateProvidedExternally)
dm.Status.URL.Scheme = "https"
return []netv1alpha1.IngressTLS{{
Hosts: []string{dm.Name},
SecretName: dm.Spec.TLS.SecretName,
SecretNamespace: dm.Namespace,
}}, nil, nil
}

if !autoTLSEnabled(ctx, dm) {
dm.Status.MarkTLSNotEnabled(v1.AutoTLSNotEnabledMessage)
return nil, nil, nil
Expand Down
55 changes: 55 additions & 0 deletions pkg/reconciler/domainmapping/table_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -1108,6 +1108,49 @@ func TestReconcileTLSEnabled(t *testing.T) {
WantEvents: []string{
Eventf(corev1.EventTypeNormal, "FinalizerUpdate", "Updated %q finalizers", "challenged.com"),
},
}, {
Name: "TLS secret provided",
Key: "default/certificateless.com",
Objects: []runtime.Object{
ksvc("default", "ready", "ready.default.svc.cluster.local", ""),
domainMapping("default", "certificateless.com",
withTLSSecret("tls-secret"),
withRef("default", "ready"),
withURL("https", "certificateless.com"),
withAddress("https", "certificateless.com"),
),
resources.MakeDomainClaim(domainMapping("default", "certificateless.com", withRef("default", "ready"))),
},
WantCreates: []runtime.Object{
ingress(domainMapping("default", "certificateless.com", withRef("default", "ready")), "the-ingress-class",
withIngressHTTPOption(netv1alpha1.HTTPOptionRedirected),
withIngressTLS(netv1alpha1.IngressTLS{
Hosts: []string{"certificateless.com"},
SecretName: "tls-secret",
SecretNamespace: "default",
})),
},
WantStatusUpdates: []clientgotesting.UpdateActionImpl{{
Object: domainMapping("default", "certificateless.com",
withRef("default", "ready"),
withURL("https", "certificateless.com"),
withAddress("https", "certificateless.com"),
withTLSSecret("tls-secret"),
withInitDomainMappingConditions,
withCertificateReady,
withDomainClaimed,
withReferenceResolved,
withCertificateNotRequired,
withIngressNotConfigured,
),
}},
WantPatches: []clientgotesting.PatchActionImpl{
patchAddFinalizerAction("default", "certificateless.com"),
},
WantEvents: []string{
Eventf(corev1.EventTypeNormal, "FinalizerUpdate", "Updated %q finalizers", "certificateless.com"),
Eventf(corev1.EventTypeNormal, "Created", "Created Ingress %q", "certificateless.com"),
},
}}

table.Test(t, MakeFactory(func(ctx context.Context, listers *Listers, cmw configmap.Watcher) controller.Reconciler {
Expand Down Expand Up @@ -1276,6 +1319,18 @@ func withPropagatedStatus(status netv1alpha1.IngressStatus) domainMappingOption
}
}

func withTLSSecret(secretName string) domainMappingOption {
return func(r *v1alpha1.DomainMapping) {
r.Spec.TLS = &v1alpha1.SecretTLS{
SecretName: secretName,
}
}
}

func withCertificateNotRequired(dm *v1alpha1.DomainMapping) {
dm.Status.MarkCertificateNotRequired(v1alpha1.TLSCertificateProvidedExternally)
}

func withInitDomainMappingConditions(dm *v1alpha1.DomainMapping) {
dm.Status.InitializeConditions()
}
Expand Down
Loading