;; disfluid, implementation of the Solid specification ;; Copyright (C) 2020, 2021 Vivien Kraus ;; This program is free software: you can redistribute it and/or modify ;; it under the terms of the GNU Affero General Public License as ;; published by the Free Software Foundation, either version 3 of the ;; License, or (at your option) any later version. ;; This program is distributed in the hope that it will be useful, ;; but WITHOUT ANY WARRANTY; without even the implied warranty of ;; MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the ;; GNU Affero General Public License for more details. ;; You should have received a copy of the GNU Affero General Public License ;; along with this program. If not, see . (define-module (tests oidc-configuration) #:use-module (webid-oidc oidc-configuration) #:use-module (webid-oidc jwk) #:use-module (webid-oidc cache) #:use-module (webid-oidc testing) #:use-module ((webid-oidc stubs) #:prefix stubs:) #:use-module ((webid-oidc parameters) #:prefix p:) #:use-module (web uri) #:use-module (web response) #:use-module (srfi srfi-19) #:use-module (ice-9 receive) #:use-module (oop goops) #:duplicates (merge-generics)) (with-test-environment "oidc-configuration" (lambda () (define* (respond uri #:key (headers '())) (unless (null? headers) (exit 1)) (when (string? uri) (set! uri (string->uri uri))) (cond ((string=? (uri->string uri) "https://example.com/keys") (values (build-response #:headers `((expires . ,(time-utc->date (make-time time-utc 0 10))) (content-type application/json))) "{ \"keys\": [ { \"e\": \"AQAB\", \"use\": \"sig\", \"kid\": \"dedc012d07f52aedfd5f97784e1bcbe23c19724d\", \"n\": \"sV158-MQ-5-sP2iTJibiMap1ug8tNY97laOud3Se_3jd4INq36NwhLpgU3FC5SCfJOs9wehTLzv_hBuo-sW0JNjAEtMEE-SDtx5486gjymDR-5Iwv7bgt25tD0cDgiboZLt1RLn-nP-V3zgYHZa_s9zLjpNyArsWWcSh6tWe2R8yW6BqS8l4_9z8jkKeyAwWmdpkY8BtKS0zZ9yljiCxKvs8CKjfHmrayg45sZ8V1-aRcjtR2ECxATHjE8L96_oNddZ-rj2axf2vTmnkx3OvIMgx0tZ0ycMG6Wy8wxxaR5ir2LV3Gkyfh72U7tI8Q1sokPmH6G62JcduNY66jEQlvQ\", \"alg\": \"RS256\", \"kty\": \"RSA\" }, { \"alg\": \"RS256\", \"kid\": \"2e3025f26b595f96eac907cc2b9471422bcaeb93\", \"e\": \"AQAB\", \"use\": \"sig\", \"kty\": \"RSA\", \"n\": \"syWuIlYmoWSl5rBQGOtYGwO5OCCZnhoWBCyl-x5gby5ofc4HNhBoVVMUggk-f_MH-pyMI5yRYsS_aPQ2bmSox2s4i9cPhxqtSAYMhTPwSwQ2BROC7xxi_N0ovp5Ivut5q8TwAn5kQZa_jR9d7JO20BUB7UqbMkBsqg2J8QTtMJ9YtA5BmUn4Y6vhIjTFtvrA6iM4i1cKoUD5Rirt5CYpcKwsLxBZbVk4E4rqgv7G0UlWt6NAs-z7XDkchlNBVpMUuiUBzxHl4LChc7dsWXRaO5vhu3j_2WnxuWCQZPlGoB51jD_ynZ027hhIcoa_tXg28_qb5Al78ZttiRCQDKueAQ\" } ] } ")) ((string=? (uri->string uri) "https://example.com/.well-known/openid-configuration") (values (build-response #:headers `((expires . ,(time-utc->date (make-time time-utc 0 10))) (content-type application/json))) "{ \"issuer\": \"https://accounts.google.com\", \"authorization_endpoint\": \"https://accounts.google.com/o/oauth2/v2/auth\", \"device_authorization_endpoint\": \"https://oauth2.googleapis.com/device/code\", \"token_endpoint\": \"https://oauth2.googleapis.com/token\", \"userinfo_endpoint\": \"https://openidconnect.googleapis.com/v1/userinfo\", \"revocation_endpoint\": \"https://oauth2.googleapis.com/revoke\", \"jwks_uri\": \"https://example.com/keys\", \"response_types_supported\": [ \"code\", \"token\", \"id_token\", \"code token\", \"code id_token\", \"token id_token\", \"code token id_token\", \"none\" ], \"subject_types_supported\": [ \"public\" ], \"id_token_signing_alg_values_supported\": [ \"RS256\" ], \"scopes_supported\": [ \"openid\", \"email\", \"profile\" ], \"token_endpoint_auth_methods_supported\": [ \"client_secret_post\", \"client_secret_basic\" ], \"claims_supported\": [ \"aud\", \"email\", \"email_verified\", \"exp\", \"family_name\", \"given_name\", \"iat\", \"iss\", \"locale\", \"name\", \"picture\", \"sub\" ], \"code_challenge_methods_supported\": [ \"plain\", \"S256\" ], \"solid_oidc_supported\": \"https://solidproject.org/TR/solid-oidc\" }")) (else (exit 2)))) (parameterize ((p:anonymous-http-request respond) (p:current-date 0)) ;; for the cache (use-cache (lambda () (define cfg (make #:server "example.com")) (define my-jwks (jwks cfg)) (unless (is-a? cfg ) (exit 3)) (unless (is-a? my-jwks ) (exit 4)) (let ((my-oidc (make #:jwks-uri "https://example.com/keys" #:authorization-endpoint "https://example.com/authorize" #:token-endpoint "https://example.com/token" #:solid-oidc-supported "https://solidproject.org/TR/solid-oidc"))) (receive (response response-body) (serve my-oidc (time-utc->date (make-time time-utc 0 3600))) (unless (eqv? (car (response-content-type response)) 'application/json) (exit 5)) (let ((parsed (->json-data (make #:json-data (stubs:json-string->scm response-body))))) (unless (equal? (assq-ref parsed 'jwks_uri) "https://example.com/keys") (exit 7)) (unless (equal? (assq-ref parsed 'authorization_endpoint) "https://example.com/authorize") (exit 8)) (unless (equal? (assq-ref parsed 'token_endpoint) "https://example.com/token") (exit 9)) (unless (equal? (assq-ref parsed 'solid_oidc_supported) "https://solidproject.org/TR/solid-oidc") (exit 10))))))))))