001/*
002 * nimbus-jose-jwt
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.jose.jwk.gen;
019
020
021import java.security.SecureRandom;
022
023import com.nimbusds.jose.JOSEException;
024import com.nimbusds.jose.jwk.OctetSequenceKey;
025import com.nimbusds.jose.util.Base64URL;
026
027
028/**
029 * Octet sequence JSON Web Key (JWK) generator.
030 *
031 * @author Vladimir Dzhuvinov
032 * @author Justin Cranford
033 * @version 2023-01-02
034 */
035public class OctetSequenceKeyGenerator extends JWKGenerator<OctetSequenceKey> {
036        
037        
038        /**
039         * The minimum size of generated keys.
040         */
041        public static final int MIN_KEY_SIZE_BITS = 112;
042        
043        
044        /**
045         * The key size, in bits.
046         */
047        private final int size;
048
049        
050        /**
051         * Creates a new octet sequence JWK generator.
052         *
053         * @param size The key size, in bits. Must be at least 112 bits long
054         *             for sufficient entropy.
055         */
056        public OctetSequenceKeyGenerator(final int size) {
057                if (size < MIN_KEY_SIZE_BITS) {
058                        throw new IllegalArgumentException("The key size must be at least " + MIN_KEY_SIZE_BITS + " bits");
059                }
060                if (size % 8 != 0) {
061                        throw new IllegalArgumentException("The key size in bits must be divisible by 8");
062                }
063                this.size = size;
064        }
065
066        
067        @Override
068        public OctetSequenceKey generate()
069                throws JOSEException {
070                
071                byte[] keyMaterial = new byte[size / 8];
072                
073                if (secureRandom != null) {
074                        secureRandom.nextBytes(keyMaterial);
075                } else {
076                        // The default random gen
077                        new SecureRandom().nextBytes(keyMaterial);
078                }
079                
080                OctetSequenceKey.Builder builder = new OctetSequenceKey.Builder(Base64URL.encode(keyMaterial))
081                        .keyUse(use)
082                        .keyOperations(ops)
083                        .algorithm(alg)
084                        .keyStore(keyStore);
085                
086                if (x5tKid) {
087                        builder.keyIDFromThumbprint();
088                } else {
089                        builder.keyID(kid);
090                }
091                
092                return builder.build();
093        }
094}