PublicKeyCredentialDescriptor.java

1
// Copyright (c) 2018, Yubico AB
2
// All rights reserved.
3
//
4
// Redistribution and use in source and binary forms, with or without
5
// modification, are permitted provided that the following conditions are met:
6
//
7
// 1. Redistributions of source code must retain the above copyright notice, this
8
//    list of conditions and the following disclaimer.
9
//
10
// 2. Redistributions in binary form must reproduce the above copyright notice,
11
//    this list of conditions and the following disclaimer in the documentation
12
//    and/or other materials provided with the distribution.
13
//
14
// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
15
// AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
16
// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17
// DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE
18
// FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
19
// DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
20
// SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
21
// CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
22
// OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
23
// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24
25
package com.yubico.webauthn.data;
26
27
import com.fasterxml.jackson.annotation.JsonCreator;
28
import com.fasterxml.jackson.annotation.JsonProperty;
29
import com.yubico.internal.util.CollectionUtil;
30
import com.yubico.internal.util.ComparableUtil;
31
import com.yubico.webauthn.RegistrationResult;
32
import com.yubico.webauthn.ToPublicKeyCredentialDescriptor;
33
import java.util.Optional;
34
import java.util.Set;
35
import java.util.SortedSet;
36
import java.util.TreeSet;
37
import lombok.Builder;
38
import lombok.NonNull;
39
import lombok.Value;
40
41
/**
42
 * The attributes that are specified by a caller when referring to a public key credential as an
43
 * input parameter to the <code>navigator.credentials.create()</code> or <code>
44
 * navigator.credentials.get()</code> methods. It mirrors the fields of the {@link
45
 * PublicKeyCredential} object returned by the latter methods.
46
 *
47
 * @see <a
48
 *     href="https://www.w3.org/TR/2021/REC-webauthn-2-20210408/#dictdef-publickeycredentialdescriptor">§5.10.3.
49
 *     Credential Descriptor (dictionary PublicKeyCredentialDescriptor)</a>
50
 */
51
@Value
52
@Builder(toBuilder = true)
53
public class PublicKeyCredentialDescriptor
54
    implements Comparable<PublicKeyCredentialDescriptor>, ToPublicKeyCredentialDescriptor {
55
56
  /** The type of the credential the caller is referring to. */
57
  @NonNull @Builder.Default
58
  private final PublicKeyCredentialType type = PublicKeyCredentialType.PUBLIC_KEY;
59
60
  /** The credential ID of the public key credential the caller is referring to. */
61
  @NonNull private final ByteArray id;
62
63
  /**
64
   * An OPTIONAL hint as to how the client might communicate with the managing authenticator of the
65
   * public key credential the caller is referring to.
66
   *
67
   * <p>This SHOULD be stored along with the {@link #getId() id} and used unmodified whenever
68
   * creating a {@link PublicKeyCredentialDescriptor} for this credential.
69
   */
70
  private final SortedSet<AuthenticatorTransport> transports;
71
72
  @JsonCreator
73
  private PublicKeyCredentialDescriptor(
74 1 1. <init> : negated conditional → KILLED
      @NonNull @JsonProperty("type") PublicKeyCredentialType type,
75 1 1. <init> : negated conditional → KILLED
      @NonNull @JsonProperty("id") ByteArray id,
76
      @JsonProperty("transports") Set<AuthenticatorTransport> transports) {
77
    this.type = type;
78
    this.id = id;
79
    this.transports =
80 1 1. <init> : negated conditional → KILLED
        transports == null ? null : CollectionUtil.immutableSortedSet(new TreeSet<>(transports));
81
  }
82
83
  @Override
84
  public int compareTo(PublicKeyCredentialDescriptor other) {
85
    int idComparison = id.compareTo(other.id);
86 1 1. compareTo : negated conditional → KILLED
    if (idComparison != 0) {
87 1 1. compareTo : replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → KILLED
      return idComparison;
88
    }
89
90 1 1. compareTo : negated conditional → KILLED
    if (type.compareTo(other.type) != 0) {
91 1 1. compareTo : replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → NO_COVERAGE
      return type.compareTo(other.type);
92
    }
93
94 2 1. compareTo : negated conditional → KILLED
2. compareTo : negated conditional → KILLED
    if (!getTransports().isPresent() && other.getTransports().isPresent()) {
95 1 1. compareTo : replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → SURVIVED
      return -1;
96 2 1. compareTo : negated conditional → KILLED
2. compareTo : negated conditional → KILLED
    } else if (getTransports().isPresent() && !other.getTransports().isPresent()) {
97 1 1. compareTo : replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → SURVIVED
      return 1;
98 2 1. compareTo : negated conditional → KILLED
2. compareTo : negated conditional → KILLED
    } else if (getTransports().isPresent() && other.getTransports().isPresent()) {
99
      int transportsComparison =
100
          ComparableUtil.compareComparableSets(getTransports().get(), other.getTransports().get());
101 1 1. compareTo : negated conditional → KILLED
      if (transportsComparison != 0) {
102 1 1. compareTo : replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → KILLED
        return transportsComparison;
103
      }
104
    }
105
106
    return 0;
107
  }
108
109
  public static PublicKeyCredentialDescriptorBuilder.MandatoryStages builder() {
110 1 1. builder : replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::builder → KILLED
    return new PublicKeyCredentialDescriptorBuilder.MandatoryStages();
111
  }
112
113
  /**
114
   * This implementation of {@link
115
   * ToPublicKeyCredentialDescriptor#toPublicKeyCredentialDescriptor()} is a no-op which returns
116
   * <code>this</code> unchanged.
117
   *
118
   * @return <code>this</code>.
119
   */
120
  @Override
121
  public PublicKeyCredentialDescriptor toPublicKeyCredentialDescriptor() {
122 1 1. toPublicKeyCredentialDescriptor : replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::toPublicKeyCredentialDescriptor → KILLED
    return this;
123
  }
124
125
  public static class PublicKeyCredentialDescriptorBuilder {
126
    private Set<AuthenticatorTransport> transports = null;
127
128
    public static class MandatoryStages {
129
      private final PublicKeyCredentialDescriptorBuilder builder =
130
          new PublicKeyCredentialDescriptorBuilder();
131
132
      /**
133
       * {@link PublicKeyCredentialDescriptorBuilder#id(ByteArray) id} is a required parameter.
134
       *
135
       * @see PublicKeyCredentialDescriptorBuilder#id(ByteArray)
136
       */
137
      public PublicKeyCredentialDescriptorBuilder id(ByteArray id) {
138 1 1. id : replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor$PublicKeyCredentialDescriptorBuilder$MandatoryStages::id → KILLED
        return builder.id(id);
139
      }
140
    }
141
142
    /**
143
     * An OPTIONAL hint as to how the client might communicate with the managing authenticator of
144
     * the public key credential the caller is referring to.
145
     *
146
     * <p>This SHOULD be set to the unmodified value returned from {@link
147
     * RegistrationResult#getKeyId()}.{@link #getTransports()} when the credential was registered.
148
     */
149
    public PublicKeyCredentialDescriptorBuilder transports(
150 1 1. transports : negated conditional → KILLED
        @NonNull Optional<Set<AuthenticatorTransport>> transports) {
151 1 1. transports : replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor$PublicKeyCredentialDescriptorBuilder::transports → KILLED
      return this.transports(transports.orElse(null));
152
    }
153
154
    /**
155
     * An OPTIONAL hint as to how the client might communicate with the managing authenticator of
156
     * the public key credential the caller is referring to.
157
     *
158
     * <p>This SHOULD be set to the unmodified value returned from {@link
159
     * RegistrationResult#getKeyId()}.{@link #getTransports()} when the credential was registered.
160
     */
161
    public PublicKeyCredentialDescriptorBuilder transports(Set<AuthenticatorTransport> transports) {
162
      this.transports = transports;
163 1 1. transports : replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor$PublicKeyCredentialDescriptorBuilder::transports → KILLED
      return this;
164
    }
165
  }
166
167
  public Optional<SortedSet<AuthenticatorTransport>> getTransports() {
168 1 1. getTransports : replaced return value with Optional.empty for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::getTransports → KILLED
    return Optional.ofNullable(transports);
169
  }
170
}

Mutations

74

1.1
Location : <init>
Killed by : com.yubico.webauthn.RelyingPartyUserIdentificationSpec
negated conditional → KILLED

75

1.1
Location : <init>
Killed by : com.yubico.webauthn.RelyingPartyUserIdentificationSpec
negated conditional → KILLED

80

1.1
Location : <init>
Killed by : com.yubico.webauthn.RelyingPartyUserIdentificationSpec
negated conditional → KILLED

86

1.1
Location : compareTo
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
negated conditional → KILLED

87

1.1
Location : compareTo
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → KILLED

90

1.1
Location : compareTo
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
negated conditional → KILLED

91

1.1
Location : compareTo
Killed by : none
replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → NO_COVERAGE

94

1.1
Location : compareTo
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
negated conditional → KILLED

2.2
Location : compareTo
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
negated conditional → KILLED

95

1.1
Location : compareTo
Killed by : none
replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → SURVIVED

96

1.1
Location : compareTo
Killed by : com.yubico.webauthn.data.BuildersSpec
negated conditional → KILLED

2.2
Location : compareTo
Killed by : com.yubico.webauthn.data.BuildersSpec
negated conditional → KILLED

97

1.1
Location : compareTo
Killed by : none
replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → SURVIVED

98

1.1
Location : compareTo
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
negated conditional → KILLED

2.2
Location : compareTo
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
negated conditional → KILLED

101

1.1
Location : compareTo
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
negated conditional → KILLED

102

1.1
Location : compareTo
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
replaced int return with 0 for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::compareTo → KILLED

110

1.1
Location : builder
Killed by : com.yubico.webauthn.RelyingPartyUserIdentificationSpec
replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::builder → KILLED

122

1.1
Location : toPublicKeyCredentialDescriptor
Killed by : com.yubico.webauthn.RelyingPartyV2AssertionSpec
replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::toPublicKeyCredentialDescriptor → KILLED

138

1.1
Location : id
Killed by : com.yubico.webauthn.RelyingPartyUserIdentificationSpec
replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor$PublicKeyCredentialDescriptorBuilder$MandatoryStages::id → KILLED

150

1.1
Location : transports
Killed by : com.yubico.webauthn.RelyingPartyUserIdentificationSpec
negated conditional → KILLED

151

1.1
Location : transports
Killed by : com.yubico.webauthn.RelyingPartyUserIdentificationSpec
replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor$PublicKeyCredentialDescriptorBuilder::transports → KILLED

163

1.1
Location : transports
Killed by : com.yubico.webauthn.RelyingPartyUserIdentificationSpec
replaced return value with null for com/yubico/webauthn/data/PublicKeyCredentialDescriptor$PublicKeyCredentialDescriptorBuilder::transports → KILLED

168

1.1
Location : getTransports
Killed by : com.yubico.webauthn.RelyingPartyStartOperationSpec
replaced return value with Optional.empty for com/yubico/webauthn/data/PublicKeyCredentialDescriptor::getTransports → KILLED

Active mutators

Tests examined


Report generated by PIT 1.15.0