Describe the bug
Unexpected error while importing symmetric key.
I added the code provided below in the samples/java for the Azure-security-keyvault-keys project and executed it. The symmetric key import failed.
Exception or Stack Trace
SLF4J: Failed to load class "org.slf4j.impl.StaticLoggerBinder".
SLF4J: Defaulting to no-operation (NOP) logger implementation
SLF4J: See http://www.slf4j.org/codes.html#StaticLoggerBinder for further details.
Exception in thread "main" com.azure.core.exception.HttpResponseException: Status code 400, "{"error":{"code":"BadParameter","message":"Invalid kty value: oct","innererror":{"code":"KeyTypeNotSupported"}}}"
at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at java.base/jdk.internal.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at java.base/jdk.internal.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.base/java.lang.reflect.Constructor.newInstance(Constructor.java:490)
at com.azure.core.http.rest.RestProxy.instantiateUnexpectedException(RestProxy.java:320)
at com.azure.core.http.rest.RestProxy.lambda$ensureExpectedStatus$3(RestProxy.java:361)
at reactor.core.publisher.MonoFlatMap$FlatMapMain.onNext(MonoFlatMap.java:118)
at reactor.core.publisher.Operators$MonoSubscriber.complete(Operators.java:1755)
at reactor.core.publisher.MonoCacheTime$CoordinatorSubscriber.signalCached(MonoCacheTime.java:320)
at reactor.core.publisher.MonoCacheTime$CoordinatorSubscriber.onNext(MonoCacheTime.java:337)
at reactor.core.publisher.Operators$ScalarSubscription.request(Operators.java:2317)
at reactor.core.publisher.MonoCacheTime$CoordinatorSubscriber.onSubscribe(MonoCacheTime.java:276)
at reactor.core.publisher.FluxFlatMap.trySubscribeScalarMap(FluxFlatMap.java:191)
at reactor.core.publisher.MonoFlatMap.subscribeOrReturn(MonoFlatMap.java:53)
at reactor.core.publisher.InternalMonoOperator.subscribe(InternalMonoOperator.java:57)
at reactor.core.publisher.MonoDefer.subscribe(MonoDefer.java:52)
at reactor.core.publisher.MonoCacheTime.subscribeOrReturn(MonoCacheTime.java:132)
at reactor.core.publisher.InternalMonoOperator.subscribe(InternalMonoOperator.java:57)
at reactor.core.publisher.MonoFlatMap$FlatMapMain.onNext(MonoFlatMap.java:150)
at reactor.core.publisher.FluxMap$MapSubscriber.onNext(FluxMap.java:114)
at reactor.core.publisher.FluxDoFinally$DoFinallySubscriber.onNext(FluxDoFinally.java:123)
at reactor.core.publisher.FluxHandle$HandleSubscriber.onNext(FluxHandle.java:112)
at reactor.core.publisher.FluxMap$MapConditionalSubscriber.onNext(FluxMap.java:213)
at reactor.core.publisher.FluxDoFinally$DoFinallySubscriber.onNext(FluxDoFinally.java:123)
at reactor.core.publisher.FluxHandleFuseable$HandleFuseableSubscriber.onNext(FluxHandleFuseable.java:178)
at reactor.core.publisher.FluxContextStart$ContextStartSubscriber.onNext(FluxContextStart.java:96)
at reactor.core.publisher.Operators$MonoSubscriber.complete(Operators.java:1755)
at reactor.core.publisher.MonoCollectList$MonoCollectListSubscriber.onComplete(MonoCollectList.java:121)
at reactor.core.publisher.FluxPeek$PeekSubscriber.onComplete(FluxPeek.java:252)
at reactor.core.publisher.FluxMap$MapSubscriber.onComplete(FluxMap.java:136)
at reactor.netty.channel.FluxReceive.onInboundComplete(FluxReceive.java:366)
at reactor.netty.channel.ChannelOperations.onInboundComplete(ChannelOperations.java:367)
at reactor.netty.channel.ChannelOperations.terminate(ChannelOperations.java:423)
at reactor.netty.http.client.HttpClientOperations.onInboundNext(HttpClientOperations.java:607)
at reactor.netty.channel.ChannelOperationsHandler.channelRead(ChannelOperationsHandler.java:96)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
at io.netty.channel.CombinedChannelDuplexHandler$DelegatingChannelHandlerContext.fireChannelRead(CombinedChannelDuplexHandler.java:436)
at io.netty.handler.codec.ByteToMessageDecoder.fireChannelRead(ByteToMessageDecoder.java:324)
at io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:296)
at io.netty.channel.CombinedChannelDuplexHandler.channelRead(CombinedChannelDuplexHandler.java:251)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
at io.netty.handler.ssl.SslHandler.unwrap(SslHandler.java:1518)
at io.netty.handler.ssl.SslHandler.decodeNonJdkCompatible(SslHandler.java:1279)
at io.netty.handler.ssl.SslHandler.decode(SslHandler.java:1316)
at io.netty.handler.codec.ByteToMessageDecoder.decodeRemovalReentryProtection(ByteToMessageDecoder.java:501)
at io.netty.handler.codec.ByteToMessageDecoder.callDecode(ByteToMessageDecoder.java:440)
at io.netty.handler.codec.ByteToMessageDecoder.channelRead(ByteToMessageDecoder.java:276)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
at io.netty.channel.AbstractChannelHandlerContext.fireChannelRead(AbstractChannelHandlerContext.java:357)
at io.netty.channel.DefaultChannelPipeline$HeadContext.channelRead(DefaultChannelPipeline.java:1410)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:379)
at io.netty.channel.AbstractChannelHandlerContext.invokeChannelRead(AbstractChannelHandlerContext.java:365)
at io.netty.channel.DefaultChannelPipeline.fireChannelRead(DefaultChannelPipeline.java:919)
at io.netty.channel.nio.AbstractNioByteChannel$NioByteUnsafe.read(AbstractNioByteChannel.java:163)
at io.netty.channel.nio.NioEventLoop.processSelectedKey(NioEventLoop.java:714)
at io.netty.channel.nio.NioEventLoop.processSelectedKeysOptimized(NioEventLoop.java:650)
at io.netty.channel.nio.NioEventLoop.processSelectedKeys(NioEventLoop.java:576)
at io.netty.channel.nio.NioEventLoop.run(NioEventLoop.java:493)
at io.netty.util.concurrent.SingleThreadEventExecutor$4.run(SingleThreadEventExecutor.java:989)
at io.netty.util.internal.ThreadExecutorMap$2.run(ThreadExecutorMap.java:74)
at io.netty.util.concurrent.FastThreadLocalRunnable.run(FastThreadLocalRunnable.java:30)
at java.base/java.lang.Thread.run(Thread.java:834)
Suppressed: java.lang.Exception: #block terminated with an error
at reactor.core.publisher.BlockingSingleSubscriber.blockingGet(BlockingSingleSubscriber.java:99)
at reactor.core.publisher.Mono.block(Mono.java:1678)
at com.azure.security.keyvault.keys.KeyClient.importKeyWithResponse(KeyClient.java:317)
at com.azure.security.keyvault.keys.KeyClient.importKey(KeyClient.java:264)
at com.saurabh500.samples.ImportKey.main(ImportKey.java:28)
To Reproduce
public class ImportKey {
public static void main(String[] args) throws InterruptedException, IllegalArgumentException {
// Instantiate a key client that will be used to call the service. Notice that the client is using default Azure
// credentials. To make default credentials work, ensure that environment variables 'AZURE_CLIENT_ID',
// 'AZURE_CLIENT_KEY' and 'AZURE_TENANT_ID' are set with the service principal credentials.
String keyVaultName = System.getenv("KEY_VAULT_NAME");
String kvUri = "https://" + keyVaultName + ".vault.azure.net";
KeyClient client = new KeyClientBuilder().vaultUrl(kvUri)
.credential(new DefaultAzureCredentialBuilder().build()).buildClient();
byte[] symmetrickeyContent = { 0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07, 0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F };
String keyName = "importedSymmetricKey";
KeyVaultKey importResult = client.importKey(keyName, JsonWebKey.fromAes(new SecretKeySpec(symmetrickeyContent, "AES")));
System.out.printf("Imported Key Id: %s Name : %s Version = %s\n", importResult.getId(),
importResult.getName());
KeyVaultKey keyvaultKey = client.getKey(keyName);
System.out.printf("Key Retrieved by name with version %s ", keyvaultKey.getProperties().getVersion());
}
}
Code Snippet
See above
Expected behavior
The call above should succeed.
Screenshots
If applicable, add screenshots to help explain your problem.
NA
Setup (please complete the following information):
Windows Server 2019EclipseAdditional context
Add any other context about the problem here.
Information Checklist
Kindly make sure that you have added all the following information above and checkoff the required fields otherwise we will treat the issuer as an incomplete report
Hi @saurabh500 馃槃 - @vcolin7 will take a look and get back to you shortly.
Hey @joshfree Good to see you here :smiley:
I am not sure if this is a service issue or client issue.
I couldn't find any references to AKV not supporting symmetric keys with kty=oct, although the error is coming from the service.
I did see another reference to similar problem at https://feedback.azure.com/forums/906355-azure-key-vault/suggestions/37894861-does-azure-support-aes-symmetric-keys-we-have-t
@vcolin7 In case you need more information like the Key Vault name or a repro environment / service details, please ping me on my Microsoft Alias: sausing
Hi @saurabh500, I am actively looking into this and will reach the Key Vault service team about it as well. I was able to reproduce the issue with the code you provided, thank you for that :)
For the time being, only EC and RSA keys are supported by KeyVault as specified here. However, I do agree documentation such as this could be clearer about whether the types mentioned are supported or not, instead of saying "these are the possible JWK types as per the specification", otherwise it feels somewhat ambiguous.
I will be closing this for the time being as it is not a bug in the SDK. Thank you for taking time to file this issue :)
Thank you. I needed a clear answer which you provided 馃榾