001/* 002 * oauth2-oidc-sdk 003 * 004 * Copyright 2012-2016, Connect2id Ltd and contributors. 005 * 006 * Licensed under the Apache License, Version 2.0 (the "License"); you may not use 007 * this file except in compliance with the License. You may obtain a copy of the 008 * License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software distributed 013 * under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR 014 * CONDITIONS OF ANY KIND, either express or implied. See the License for the 015 * specific language governing permissions and limitations under the License. 016 */ 017 018package com.nimbusds.openid.connect.sdk.rp; 019 020 021import java.net.URI; 022import java.net.URISyntaxException; 023import java.util.*; 024 025import com.nimbusds.jose.EncryptionMethod; 026import com.nimbusds.jose.JWEAlgorithm; 027import com.nimbusds.jose.JWSAlgorithm; 028import com.nimbusds.oauth2.sdk.ParseException; 029import com.nimbusds.oauth2.sdk.client.ClientMetadata; 030import com.nimbusds.oauth2.sdk.client.RegistrationError; 031import com.nimbusds.oauth2.sdk.util.JSONObjectUtils; 032import com.nimbusds.openid.connect.sdk.SubjectType; 033import com.nimbusds.openid.connect.sdk.claims.ACR; 034import com.nimbusds.openid.connect.sdk.id.SectorID; 035import net.minidev.json.JSONArray; 036import net.minidev.json.JSONObject; 037import org.apache.commons.collections.CollectionUtils; 038 039 040/** 041 * OpenID Connect client metadata. 042 * 043 * <p>Related specifications: 044 * 045 * <ul> 046 * <li>OpenID Connect Dynamic Client Registration 1.0, section 2. 047 * <li>OpenID Connect Session Management 1.0, section 5.1.1. 048 * <li>OAuth 2.0 Dynamic Client Registration Protocol (RFC 7591), section 049 * 2. 050 * </ul> 051 */ 052public class OIDCClientMetadata extends ClientMetadata { 053 054 055 /** 056 * The registered parameter names. 057 */ 058 private static final Set<String> REGISTERED_PARAMETER_NAMES; 059 060 061 /** 062 * Initialises the registered parameter name set. 063 */ 064 static { 065 // Start with the base OAuth 2.0 client params 066 Set<String> p = new HashSet<>(ClientMetadata.getRegisteredParameterNames()); 067 068 // OIDC params 069 p.add("application_type"); 070 p.add("subject_type"); 071 p.add("sector_identifier_uri"); 072 p.add("request_uris"); 073 p.add("request_object_signing_alg"); 074 p.add("request_object_encryption_alg"); 075 p.add("request_object_encryption_enc"); 076 p.add("id_token_signed_response_alg"); 077 p.add("id_token_encrypted_response_alg"); 078 p.add("id_token_encrypted_response_enc"); 079 p.add("userinfo_signed_response_alg"); 080 p.add("userinfo_encrypted_response_alg"); 081 p.add("userinfo_encrypted_response_enc"); 082 p.add("default_max_age"); 083 p.add("require_auth_time"); 084 p.add("default_acr_values"); 085 p.add("initiate_login_uri"); 086 087 // OIDC session 088 p.add("post_logout_redirect_uris"); 089 090 REGISTERED_PARAMETER_NAMES = Collections.unmodifiableSet(p); 091 } 092 093 094 /** 095 * The client application type. 096 */ 097 private ApplicationType applicationType; 098 099 100 /** 101 * The subject identifier type for responses to this client. 102 */ 103 private SubjectType subjectType; 104 105 106 /** 107 * Sector identifier URI. 108 */ 109 private URI sectorIDURI; 110 111 112 /** 113 * Pre-registered OpenID Connect request URIs. 114 */ 115 private Set<URI> requestObjectURIs; 116 117 118 /** 119 * The JSON Web Signature (JWS) algorithm required for the OpenID 120 * Connect request objects sent by this client. 121 */ 122 private JWSAlgorithm requestObjectJWSAlg; 123 124 125 /** 126 * The JSON Web Encryption (JWE) algorithm required for the OpenID 127 * Connect request objects sent by this client. 128 */ 129 private JWEAlgorithm requestObjectJWEAlg; 130 131 132 /** 133 * The JSON Web Encryption (JWE) method required for the OpenID Connect 134 * request objects sent by this client. 135 */ 136 private EncryptionMethod requestObjectJWEEnc; 137 138 139 /** 140 * The JSON Web Signature (JWS) algorithm required for the ID Tokens 141 * issued to this client. 142 */ 143 private JWSAlgorithm idTokenJWSAlg; 144 145 146 /** 147 * The JSON Web Encryption (JWE) algorithm required for the ID Tokens 148 * issued to this client. 149 */ 150 private JWEAlgorithm idTokenJWEAlg; 151 152 153 /** 154 * The JSON Web Encryption (JWE) method required for the ID Tokens 155 * issued to this client. 156 */ 157 private EncryptionMethod idTokenJWEEnc; 158 159 160 /** 161 * The JSON Web Signature (JWS) algorithm required for the UserInfo 162 * responses to this client. 163 */ 164 private JWSAlgorithm userInfoJWSAlg; 165 166 167 /** 168 * The JSON Web Encryption (JWE) algorithm required for the UserInfo 169 * responses to this client. 170 */ 171 private JWEAlgorithm userInfoJWEAlg; 172 173 174 /** 175 * The JSON Web Encryption (JWE) method required for the UserInfo 176 * responses to this client. 177 */ 178 private EncryptionMethod userInfoJWEEnc; 179 180 181 /** 182 * The default max authentication age, in seconds. If not specified 0. 183 */ 184 private int defaultMaxAge = -1; 185 186 187 /** 188 * If {@code true} the {@code auth_time} claim in the ID Token is 189 * required by default. 190 */ 191 private boolean requiresAuthTime; 192 193 194 /** 195 * The default Authentication Context Class Reference (ACR) values, by 196 * order of preference. 197 */ 198 private List<ACR> defaultACRs; 199 200 201 /** 202 * Authorisation server initiated login HTTPS URI. 203 */ 204 private URI initiateLoginURI; 205 206 207 /** 208 * Logout redirection URIs. 209 */ 210 private Set<URI> postLogoutRedirectURIs; 211 212 213 /** 214 * Creates a new OpenID Connect client metadata instance. 215 */ 216 public OIDCClientMetadata() { 217 218 super(); 219 } 220 221 222 /** 223 * Creates a new OpenID Connect client metadata instance from the 224 * specified base OAuth 2.0 client metadata. 225 * 226 * @param metadata The base OAuth 2.0 client metadata. Must not be 227 * {@code null}. 228 */ 229 public OIDCClientMetadata(final ClientMetadata metadata) { 230 231 super(metadata); 232 } 233 234 235 /** 236 * Gets the registered (standard) OpenID Connect client metadata 237 * parameter names. 238 * 239 * @return The registered OpenID Connect parameter names, as an 240 * unmodifiable set. 241 */ 242 public static Set<String> getRegisteredParameterNames() { 243 244 return REGISTERED_PARAMETER_NAMES; 245 } 246 247 248 /** 249 * Gets the client application type. Corresponds to the 250 * {@code application_type} client metadata field. 251 * 252 * @return The client application type, {@code null} if not specified. 253 */ 254 public ApplicationType getApplicationType() { 255 256 return applicationType; 257 } 258 259 260 /** 261 * Sets the client application type. Corresponds to the 262 * {@code application_type} client metadata field. 263 * 264 * @param applicationType The client application type, {@code null} if 265 * not specified. 266 */ 267 public void setApplicationType(final ApplicationType applicationType) { 268 269 this.applicationType = applicationType; 270 } 271 272 273 /** 274 * Gets the subject identifier type for responses to this client. 275 * Corresponds to the {@code subject_type} client metadata field. 276 * 277 * @return The subject identifier type, {@code null} if not specified. 278 */ 279 public SubjectType getSubjectType() { 280 281 return subjectType; 282 } 283 284 285 /** 286 * Sets the subject identifier type for responses to this client. 287 * Corresponds to the {@code subject_type} client metadata field. 288 * 289 * @param subjectType The subject identifier type, {@code null} if not 290 * specified. 291 */ 292 public void setSubjectType(final SubjectType subjectType) { 293 294 this.subjectType = subjectType; 295 } 296 297 298 /** 299 * Gets the sector identifier URI. Corresponds to the 300 * {@code sector_identifier_uri} client metadata field. 301 * 302 * @return The sector identifier URI, {@code null} if not specified. 303 */ 304 public URI getSectorIDURI() { 305 306 return sectorIDURI; 307 } 308 309 310 /** 311 * Sets the sector identifier URI. Corresponds to the 312 * {@code sector_identifier_uri} client metadata field. 313 * 314 * @param sectorIDURI The sector identifier URI, {@code null} if not 315 * specified. 316 */ 317 public void setSectorIDURI(final URI sectorIDURI) { 318 319 if (sectorIDURI != null) { 320 SectorID.ensureHTTPScheme(sectorIDURI); 321 SectorID.ensureHostComponent(sectorIDURI); 322 } 323 324 this.sectorIDURI = sectorIDURI; 325 } 326 327 328 /** 329 * Resolves the sector identifier from the client metadata. 330 * 331 * @return The sector identifier, {@code null} if the subject type is 332 * set to public. 333 * 334 * @throws IllegalStateException If resolution failed due to incomplete 335 * or inconsistent metadata. 336 */ 337 public SectorID resolveSectorID() { 338 339 if (! SubjectType.PAIRWISE.equals(getSubjectType())) { 340 // subject type is not pairwise or null 341 return null; 342 } 343 344 // Check sector identifier URI first 345 if (getSectorIDURI() != null) { 346 return new SectorID(getSectorIDURI()); 347 } 348 349 // Check redirect URIs second 350 if (CollectionUtils.isEmpty(getRedirectionURIs())) { 351 throw new IllegalStateException("Couldn't resolve sector ID: Missing redirect_uris"); 352 } 353 354 if (getRedirectionURIs().size() > 1) { 355 throw new IllegalStateException("Couldn't resolve sector ID: More than one redirect_uri, sector_identifier_uri not specified"); 356 } 357 358 return new SectorID(getRedirectionURIs().iterator().next()); 359 } 360 361 362 /** 363 * Gets the pre-registered OpenID Connect request object URIs. 364 * Corresponds to the {@code request_uris} client metadata field. 365 * 366 * @return The request object URIs, {@code null} if not specified. 367 */ 368 public Set<URI> getRequestObjectURIs() { 369 370 return requestObjectURIs; 371 } 372 373 374 /** 375 * Sets the pre-registered OpenID Connect request object URIs. 376 * Corresponds to the {@code request_uris} client metadata field. 377 * 378 * @param requestObjectURIs The request object URIs, {@code null} if 379 * not specified. 380 */ 381 public void setRequestObjectURIs(final Set<URI> requestObjectURIs) { 382 383 this.requestObjectURIs = requestObjectURIs; 384 } 385 386 387 /** 388 * Gets the JSON Web Signature (JWS) algorithm required for the OpenID 389 * Connect request objects sent by this client. Corresponds to the 390 * {@code request_object_signing_alg} client metadata field. 391 * 392 * @return The JWS algorithm, {@code null} if not specified. 393 */ 394 public JWSAlgorithm getRequestObjectJWSAlg() { 395 396 return requestObjectJWSAlg; 397 } 398 399 400 /** 401 * Sets the JSON Web Signature (JWS) algorithm required for the OpenID 402 * Connect request objects sent by this client. Corresponds to the 403 * {@code request_object_signing_alg} client metadata field. 404 * 405 * @param requestObjectJWSAlg The JWS algorithm, {@code null} if not 406 * specified. 407 */ 408 public void setRequestObjectJWSAlg(final JWSAlgorithm requestObjectJWSAlg) { 409 410 this.requestObjectJWSAlg = requestObjectJWSAlg; 411 } 412 413 414 /** 415 * Gets the JSON Web Encryption (JWE) algorithm required for the OpenID 416 * Connect request objects sent by this client. Corresponds to the 417 * {@code request_object_encryption_alg} client metadata field. 418 * 419 * @return The JWE algorithm, {@code null} if not specified. 420 */ 421 public JWEAlgorithm getRequestObjectJWEAlg() { 422 423 return requestObjectJWEAlg; 424 } 425 426 427 /** 428 * Sets the JSON Web Encryption (JWE) algorithm required for the OpenID 429 * Connect request objects sent by this client. Corresponds to the 430 * {@code request_object_encryption_alg} client metadata field. 431 * 432 * @param requestObjectJWEAlg The JWE algorithm, {@code null} if not 433 * specified. 434 */ 435 public void setRequestObjectJWEAlg(final JWEAlgorithm requestObjectJWEAlg) { 436 437 this.requestObjectJWEAlg = requestObjectJWEAlg; 438 } 439 440 441 /** 442 * Gets the JSON Web Encryption (JWE) method required for the OpenID 443 * Connect request objects sent by this client. Corresponds to the 444 * {@code request_object_encryption_enc} client metadata field. 445 * 446 * @return The JWE method, {@code null} if not specified. 447 */ 448 public EncryptionMethod getRequestObjectJWEEnc() { 449 450 return requestObjectJWEEnc; 451 } 452 453 454 /** 455 * Sets the JSON Web Encryption (JWE) method required for the OpenID 456 * Connect request objects sent by this client. Corresponds to the 457 * {@code request_object_encryption_enc} client metadata field. 458 * 459 * @param requestObjectJWEEnc The JWE method, {@code null} if not 460 * specified. 461 */ 462 public void setRequestObjectJWEEnc(final EncryptionMethod requestObjectJWEEnc) { 463 464 this.requestObjectJWEEnc = requestObjectJWEEnc; 465 } 466 467 468 /** 469 * Gets the JSON Web Signature (JWS) algorithm required for the ID 470 * Tokens issued to this client. Corresponds to the 471 * {@code id_token_signed_response_alg} client metadata field. 472 * 473 * @return The JWS algorithm, {@code null} if not specified. 474 */ 475 public JWSAlgorithm getIDTokenJWSAlg() { 476 477 return idTokenJWSAlg; 478 } 479 480 481 /** 482 * Sets the JSON Web Signature (JWS) algorithm required for the ID 483 * Tokens issued to this client. Corresponds to the 484 * {@code id_token_signed_response_alg} client metadata field. 485 * 486 * @param idTokenJWSAlg The JWS algorithm, {@code null} if not 487 * specified. 488 */ 489 public void setIDTokenJWSAlg(final JWSAlgorithm idTokenJWSAlg) { 490 491 this.idTokenJWSAlg = idTokenJWSAlg; 492 } 493 494 495 /** 496 * Gets the JSON Web Encryption (JWE) algorithm required for the ID 497 * Tokens issued to this client. Corresponds to the 498 * {@code id_token_encrypted_response_alg} client metadata field. 499 * 500 * @return The JWE algorithm, {@code null} if not specified. 501 */ 502 public JWEAlgorithm getIDTokenJWEAlg() { 503 504 return idTokenJWEAlg; 505 } 506 507 508 /** 509 * Sets the JSON Web Encryption (JWE) algorithm required for the ID 510 * Tokens issued to this client. Corresponds to the 511 * {@code id_token_encrypted_response_alg} client metadata field. 512 * 513 * @param idTokenJWEAlg The JWE algorithm, {@code null} if not 514 * specified. 515 */ 516 public void setIDTokenJWEAlg(final JWEAlgorithm idTokenJWEAlg) { 517 518 this.idTokenJWEAlg = idTokenJWEAlg; 519 } 520 521 522 /** 523 * Gets the JSON Web Encryption (JWE) method required for the ID Tokens 524 * issued to this client. Corresponds to the 525 * {@code id_token_encrypted_response_enc} client metadata field. 526 * 527 * @return The JWE method, {@code null} if not specified. 528 */ 529 public EncryptionMethod getIDTokenJWEEnc() { 530 531 return idTokenJWEEnc; 532 } 533 534 535 /** 536 * Sets the JSON Web Encryption (JWE) method required for the ID Tokens 537 * issued to this client. Corresponds to the 538 * {@code id_token_encrypted_response_enc} client metadata field. 539 * 540 * @param idTokenJWEEnc The JWE method, {@code null} if not specified. 541 */ 542 public void setIDTokenJWEEnc(final EncryptionMethod idTokenJWEEnc) { 543 544 this.idTokenJWEEnc = idTokenJWEEnc; 545 } 546 547 548 /** 549 * Gets the JSON Web Signature (JWS) algorithm required for the 550 * UserInfo responses to this client. Corresponds to the 551 * {@code userinfo_signed_response_alg} client metadata field. 552 * 553 * @return The JWS algorithm, {@code null} if not specified. 554 */ 555 public JWSAlgorithm getUserInfoJWSAlg() { 556 557 return userInfoJWSAlg; 558 } 559 560 561 /** 562 * Sets the JSON Web Signature (JWS) algorithm required for the 563 * UserInfo responses to this client. Corresponds to the 564 * {@code userinfo_signed_response_alg} client metadata field. 565 * 566 * @param userInfoJWSAlg The JWS algorithm, {@code null} if not 567 * specified. 568 */ 569 public void setUserInfoJWSAlg(final JWSAlgorithm userInfoJWSAlg) { 570 571 this.userInfoJWSAlg = userInfoJWSAlg; 572 } 573 574 575 /** 576 * Gets the JSON Web Encryption (JWE) algorithm required for the 577 * UserInfo responses to this client. Corresponds to the 578 * {@code userinfo_encrypted_response_alg} client metadata field. 579 * 580 * @return The JWE algorithm, {@code null} if not specified. 581 */ 582 public JWEAlgorithm getUserInfoJWEAlg() { 583 584 return userInfoJWEAlg; 585 } 586 587 588 /** 589 * Sets the JSON Web Encryption (JWE) algorithm required for the 590 * UserInfo responses to this client. Corresponds to the 591 * {@code userinfo_encrypted_response_alg} client metadata field. 592 * 593 * @param userInfoJWEAlg The JWE algorithm, {@code null} if not 594 * specified. 595 */ 596 public void setUserInfoJWEAlg(final JWEAlgorithm userInfoJWEAlg) { 597 598 this.userInfoJWEAlg = userInfoJWEAlg; 599 } 600 601 602 /** 603 * Gets the JSON Web Encryption (JWE) method required for the UserInfo 604 * responses to this client. Corresponds to the 605 * {@code userinfo_encrypted_response_enc} client metadata field. 606 * 607 * @return The JWE method, {@code null} if not specified. 608 */ 609 public EncryptionMethod getUserInfoJWEEnc() { 610 611 return userInfoJWEEnc; 612 } 613 614 615 /** 616 * Sets the JSON Web Encryption (JWE) method required for the UserInfo 617 * responses to this client. Corresponds to the 618 * {@code userinfo_encrypted_response_enc} client metadata field. 619 * 620 * @param userInfoJWEEnc The JWE method, {@code null} if not specified. 621 */ 622 public void setUserInfoJWEEnc(final EncryptionMethod userInfoJWEEnc) { 623 624 this.userInfoJWEEnc = userInfoJWEEnc; 625 } 626 627 628 /** 629 * Gets the default maximum authentication age. Corresponds to the 630 * {@code default_max_age} client metadata field. 631 * 632 * @return The default max authentication age, in seconds. If not 633 * specified -1. 634 */ 635 public int getDefaultMaxAge() { 636 637 return defaultMaxAge; 638 } 639 640 641 /** 642 * Sets the default maximum authentication age. Corresponds to the 643 * {@code default_max_age} client metadata field. 644 * 645 * @param defaultMaxAge The default max authentication age, in seconds. 646 * If not specified -1. 647 */ 648 public void setDefaultMaxAge(final int defaultMaxAge) { 649 650 this.defaultMaxAge = defaultMaxAge; 651 } 652 653 654 /** 655 * Gets the default requirement for the {@code auth_time} claim in the 656 * ID Token. Corresponds to the {@code require_auth_time} client 657 * metadata field. 658 * 659 * @return If {@code true} the {@code auth_Time} claim in the ID Token 660 * is required by default. 661 */ 662 public boolean requiresAuthTime() { 663 664 return requiresAuthTime; 665 } 666 667 668 /** 669 * Sets the default requirement for the {@code auth_time} claim in the 670 * ID Token. Corresponds to the {@code require_auth_time} client 671 * metadata field. 672 * 673 * @param requiresAuthTime If {@code true} the {@code auth_Time} claim 674 * in the ID Token is required by default. 675 */ 676 public void requiresAuthTime(final boolean requiresAuthTime) { 677 678 this.requiresAuthTime = requiresAuthTime; 679 } 680 681 682 /** 683 * Gets the default Authentication Context Class Reference (ACR) 684 * values. Corresponds to the {@code default_acr_values} client 685 * metadata field. 686 * 687 * @return The default ACR values, by order of preference, 688 * {@code null} if not specified. 689 */ 690 public List<ACR> getDefaultACRs() { 691 692 return defaultACRs; 693 } 694 695 696 /** 697 * Sets the default Authentication Context Class Reference (ACR) 698 * values. Corresponds to the {@code default_acr_values} client 699 * metadata field. 700 * 701 * @param defaultACRs The default ACRs, by order of preference, 702 * {@code null} if not specified. 703 */ 704 public void setDefaultACRs(final List<ACR> defaultACRs) { 705 706 this.defaultACRs = defaultACRs; 707 } 708 709 710 /** 711 * Gets the HTTPS URI that the authorisation server can call to 712 * initiate a login at the client. Corresponds to the 713 * {@code initiate_login_uri} client metadata field. 714 * 715 * @return The login URI, {@code null} if not specified. 716 */ 717 public URI getInitiateLoginURI() { 718 719 return initiateLoginURI; 720 } 721 722 723 /** 724 * Sets the HTTPS URI that the authorisation server can call to 725 * initiate a login at the client. Corresponds to the 726 * {@code initiate_login_uri} client metadata field. 727 * 728 * @param loginURI The login URI, {@code null} if not specified. 729 */ 730 public void setInitiateLoginURI(final URI loginURI) { 731 732 this.initiateLoginURI = loginURI; 733 } 734 735 736 /** 737 * Gets the post logout redirection URIs. Corresponds to the 738 * {@code post_logout_redirect_uris} client metadata field. 739 * 740 * @return The logout redirection URIs, {@code null} if not specified. 741 */ 742 public Set<URI> getPostLogoutRedirectionURIs() { 743 744 return postLogoutRedirectURIs; 745 } 746 747 748 /** 749 * Sets the post logout redirection URIs. Corresponds to the 750 * {@code post_logout_redirect_uris} client metadata field. 751 * 752 * @param logoutURIs The logout redirection URIs, {@code null} if not 753 * specified. 754 */ 755 public void setPostLogoutRedirectionURIs(final Set<URI> logoutURIs) { 756 757 postLogoutRedirectURIs = logoutURIs; 758 } 759 760 761 /** 762 * Applies the client metadata defaults where no values have been 763 * specified. 764 * 765 * <ul> 766 * <li>The response types default to {@code ["code"]}. 767 * <li>The grant types default to {@code "authorization_code".} 768 * <li>The client authentication method defaults to 769 * "client_secret_basic". 770 * <li>The application type defaults to 771 * {@link ApplicationType#WEB}. 772 * <li>The ID token JWS algorithm defaults to "RS256". 773 * </ul> 774 */ 775 @Override 776 public void applyDefaults() { 777 778 super.applyDefaults(); 779 780 if (applicationType == null) { 781 applicationType = ApplicationType.WEB; 782 } 783 784 if (idTokenJWSAlg == null) { 785 idTokenJWSAlg = JWSAlgorithm.RS256; 786 } 787 } 788 789 790 @Override 791 public JSONObject toJSONObject() { 792 793 JSONObject o = super.toJSONObject(false); 794 795 o.putAll(getCustomFields()); 796 797 if (applicationType != null) 798 o.put("application_type", applicationType.toString()); 799 800 if (subjectType != null) 801 o.put("subject_type", subjectType.toString()); 802 803 804 if (sectorIDURI != null) 805 o.put("sector_identifier_uri", sectorIDURI.toString()); 806 807 808 if (requestObjectURIs != null) { 809 810 JSONArray uriList = new JSONArray(); 811 812 for (URI uri: requestObjectURIs) 813 uriList.add(uri.toString()); 814 815 o.put("request_uris", uriList); 816 } 817 818 819 if (requestObjectJWSAlg != null) 820 o.put("request_object_signing_alg", requestObjectJWSAlg.getName()); 821 822 if (requestObjectJWEAlg != null) 823 o.put("request_object_encryption_alg", requestObjectJWEAlg.getName()); 824 825 if (requestObjectJWEEnc != null) 826 o.put("request_object_encryption_enc", requestObjectJWEEnc.getName()); 827 828 829 if (idTokenJWSAlg != null) 830 o.put("id_token_signed_response_alg", idTokenJWSAlg.getName()); 831 832 833 if (idTokenJWEAlg != null) 834 o.put("id_token_encrypted_response_alg", idTokenJWEAlg.getName()); 835 836 837 if (idTokenJWEEnc != null) 838 o.put("id_token_encrypted_response_enc", idTokenJWEEnc.getName()); 839 840 841 if (userInfoJWSAlg != null) 842 o.put("userinfo_signed_response_alg", userInfoJWSAlg.getName()); 843 844 845 if (userInfoJWEAlg != null) 846 o.put("userinfo_encrypted_response_alg", userInfoJWEAlg.getName()); 847 848 849 if (userInfoJWEEnc != null) 850 o.put("userinfo_encrypted_response_enc", userInfoJWEEnc.getName()); 851 852 853 if (defaultMaxAge > 0) 854 o.put("default_max_age", defaultMaxAge); 855 856 857 if (requiresAuthTime()) 858 o.put("require_auth_time", requiresAuthTime); 859 860 861 if (defaultACRs != null) { 862 863 JSONArray acrList = new JSONArray(); 864 865 for (ACR acr: defaultACRs) 866 acrList.add(acr); 867 868 o.put("default_acr_values", acrList); 869 } 870 871 872 if (initiateLoginURI != null) 873 o.put("initiate_login_uri", initiateLoginURI.toString()); 874 875 876 if (postLogoutRedirectURIs != null) { 877 878 JSONArray uriList = new JSONArray(); 879 880 for (URI uri: postLogoutRedirectURIs) 881 uriList.add(uri.toString()); 882 883 o.put("post_logout_redirect_uris", uriList); 884 } 885 886 return o; 887 } 888 889 890 /** 891 * Parses an OpenID Connect client metadata instance from the specified 892 * JSON object. 893 * 894 * @param jsonObject The JSON object to parse. Must not be 895 * {@code null}. 896 * 897 * @return The OpenID Connect client metadata. 898 * 899 * @throws ParseException If the JSON object couldn't be parsed to an 900 * OpenID Connect client metadata instance. 901 */ 902 public static OIDCClientMetadata parse(final JSONObject jsonObject) 903 throws ParseException { 904 905 ClientMetadata baseMetadata = ClientMetadata.parse(jsonObject); 906 907 OIDCClientMetadata metadata = new OIDCClientMetadata(baseMetadata); 908 909 // Parse the OIDC-specific fields from the custom OAuth 2.0 dyn 910 // reg fields 911 912 JSONObject oidcFields = baseMetadata.getCustomFields(); 913 914 try { 915 if (jsonObject.containsKey("application_type")) { 916 metadata.setApplicationType(JSONObjectUtils.getEnum(jsonObject, "application_type", ApplicationType.class)); 917 oidcFields.remove("application_type"); 918 } 919 920 if (jsonObject.containsKey("subject_type")) { 921 metadata.setSubjectType(JSONObjectUtils.getEnum(jsonObject, "subject_type", SubjectType.class)); 922 oidcFields.remove("subject_type"); 923 } 924 925 if (jsonObject.containsKey("sector_identifier_uri")) { 926 metadata.setSectorIDURI(JSONObjectUtils.getURI(jsonObject, "sector_identifier_uri")); 927 oidcFields.remove("sector_identifier_uri"); 928 } 929 930 if (jsonObject.containsKey("request_uris")) { 931 932 Set<URI> requestURIs = new LinkedHashSet<>(); 933 934 for (String uriString : JSONObjectUtils.getStringArray(jsonObject, "request_uris")) { 935 936 try { 937 requestURIs.add(new URI(uriString)); 938 939 } catch (URISyntaxException e) { 940 941 throw new ParseException("Invalid \"request_uris\" parameter"); 942 } 943 } 944 945 metadata.setRequestObjectURIs(requestURIs); 946 oidcFields.remove("request_uris"); 947 } 948 949 if (jsonObject.containsKey("request_object_signing_alg")) { 950 metadata.setRequestObjectJWSAlg(new JWSAlgorithm( 951 JSONObjectUtils.getString(jsonObject, "request_object_signing_alg"))); 952 953 oidcFields.remove("request_object_signing_alg"); 954 } 955 956 if (jsonObject.containsKey("request_object_encryption_alg")) { 957 metadata.setRequestObjectJWEAlg(new JWEAlgorithm( 958 JSONObjectUtils.getString(jsonObject, "request_object_encryption_alg"))); 959 960 oidcFields.remove("request_object_encryption_alg"); 961 } 962 963 if (jsonObject.containsKey("request_object_encryption_enc")) { 964 metadata.setRequestObjectJWEEnc(EncryptionMethod.parse( 965 JSONObjectUtils.getString(jsonObject, "request_object_encryption_enc"))); 966 967 oidcFields.remove("request_object_encryption_enc"); 968 } 969 970 if (jsonObject.containsKey("id_token_signed_response_alg")) { 971 metadata.setIDTokenJWSAlg(new JWSAlgorithm( 972 JSONObjectUtils.getString(jsonObject, "id_token_signed_response_alg"))); 973 974 oidcFields.remove("id_token_signed_response_alg"); 975 } 976 977 if (jsonObject.containsKey("id_token_encrypted_response_alg")) { 978 metadata.setIDTokenJWEAlg(new JWEAlgorithm( 979 JSONObjectUtils.getString(jsonObject, "id_token_encrypted_response_alg"))); 980 981 oidcFields.remove("id_token_encrypted_response_alg"); 982 } 983 984 if (jsonObject.containsKey("id_token_encrypted_response_enc")) { 985 metadata.setIDTokenJWEEnc(EncryptionMethod.parse( 986 JSONObjectUtils.getString(jsonObject, "id_token_encrypted_response_enc"))); 987 988 oidcFields.remove("id_token_encrypted_response_enc"); 989 } 990 991 if (jsonObject.containsKey("userinfo_signed_response_alg")) { 992 metadata.setUserInfoJWSAlg(new JWSAlgorithm( 993 JSONObjectUtils.getString(jsonObject, "userinfo_signed_response_alg"))); 994 995 oidcFields.remove("userinfo_signed_response_alg"); 996 } 997 998 if (jsonObject.containsKey("userinfo_encrypted_response_alg")) { 999 metadata.setUserInfoJWEAlg(new JWEAlgorithm( 1000 JSONObjectUtils.getString(jsonObject, "userinfo_encrypted_response_alg"))); 1001 1002 oidcFields.remove("userinfo_encrypted_response_alg"); 1003 } 1004 1005 if (jsonObject.containsKey("userinfo_encrypted_response_enc")) { 1006 metadata.setUserInfoJWEEnc(EncryptionMethod.parse( 1007 JSONObjectUtils.getString(jsonObject, "userinfo_encrypted_response_enc"))); 1008 1009 oidcFields.remove("userinfo_encrypted_response_enc"); 1010 } 1011 1012 if (jsonObject.containsKey("default_max_age")) { 1013 metadata.setDefaultMaxAge(JSONObjectUtils.getInt(jsonObject, "default_max_age")); 1014 oidcFields.remove("default_max_age"); 1015 } 1016 1017 if (jsonObject.containsKey("require_auth_time")) { 1018 metadata.requiresAuthTime(JSONObjectUtils.getBoolean(jsonObject, "require_auth_time")); 1019 oidcFields.remove("require_auth_time"); 1020 } 1021 1022 if (jsonObject.containsKey("default_acr_values")) { 1023 1024 List<ACR> acrValues = new LinkedList<>(); 1025 1026 for (String acrString : JSONObjectUtils.getStringArray(jsonObject, "default_acr_values")) 1027 acrValues.add(new ACR(acrString)); 1028 1029 metadata.setDefaultACRs(acrValues); 1030 1031 oidcFields.remove("default_acr_values"); 1032 } 1033 1034 if (jsonObject.containsKey("initiate_login_uri")) { 1035 metadata.setInitiateLoginURI(JSONObjectUtils.getURI(jsonObject, "initiate_login_uri")); 1036 oidcFields.remove("initiate_login_uri"); 1037 } 1038 1039 if (jsonObject.containsKey("post_logout_redirect_uris")) { 1040 1041 Set<URI> logoutURIs = new LinkedHashSet<>(); 1042 1043 for (String uriString : JSONObjectUtils.getStringArray(jsonObject, "post_logout_redirect_uris")) { 1044 1045 try { 1046 logoutURIs.add(new URI(uriString)); 1047 1048 } catch (URISyntaxException e) { 1049 1050 throw new ParseException("Invalid \"post_logout_redirect_uris\" parameter"); 1051 } 1052 } 1053 1054 metadata.setPostLogoutRedirectionURIs(logoutURIs); 1055 oidcFields.remove("post_logout_redirect_uris"); 1056 } 1057 } catch (ParseException e) { 1058 // Insert client_client_metadata error code so that it 1059 // can be reported back to the client if we have a 1060 // registration event 1061 throw new ParseException(e.getMessage(), RegistrationError.INVALID_CLIENT_METADATA.appendDescription(": " + e.getMessage()), e.getCause()); 1062 } 1063 1064 // The remaining fields are custom 1065 metadata.setCustomFields(oidcFields); 1066 1067 return metadata; 1068 } 1069}