[ 
https://issues.apache.org/jira/browse/CASSANDRA-20484?page=com.atlassian.jira.plugin.system.issuetabpanels:comment-tabpanel&focusedCommentId=17951338#comment-17951338
 ] 

Maulin Vasavada edited comment on CASSANDRA-20484 at 5/14/25 6:54 AM:
----------------------------------------------------------------------

Okay, so few more questions,
 # When you use `-f` option to specify cassandra.yaml path, are you 
inheriting/copying the same file that you use for the Cassandra service/server? 
(i.e. either you are running sstablesloader from one of the server nodes (hence 
can access the same file) OR copied the file over to a VM where you are running 
sstableloader from)
 # If you are NOT using the same file (either by sharing the location or 
copying it over) as the server's cassandra.yaml, then you must be creating a 
new/separate cassandra.yaml file just to use it for the sstableloader, correct?
 ## If this is the case, in my opinion what you specify in the 
client_encryption_options AND server_encryption_options must be the same config 
because to the Cassandra target nodes you connect with (for native transport or 
storage port) your VM is a 'client' and whatever server configured for SSL you 
need to comply with. This means if the server configured to require_client_auth 
you will need to have keystore for providing your client certs AND truststore 
to trust server cert. If the server configured required_client_auth as false 
you ONLY need a truststore to be able to trust server cert.

Now, coming to you original question/ask - That if your config file used for 
the ssltableloader tool (not the config file inherited/copying from the 
server's config) specified the `require_client_auth` false you should not 
require truststore - does not logically make sense to me. This is because as a 
client you don't control if you require the client to auth with server or not 
and as a client if you do have to use SSL (since server configured 
client_encryption_options as enabled on its side) you MUST need a truststore 
always to be able to validate server's cert.

Btw, I do agree with your code pointers that the code is using two distinct 
paths - one to use client_encryption_options from the config file (the init() 
method in the NativeSSTableLoaderClient uses those ssl options to fetch 
metadata etc) AND second to use server_encryption_options from the config file 
for the storage port connection (via
BulkLoadConnectionFactory(serverEncOptions, storagePort) ).

Also, when I think about the sstableloader options from the documentation 
standpoint ([link|#usage]]) - From the command line it ONLY has "Client SSL" 
options overrides and not server encryption options overrides - why? I think 
its because no matter how you see sstableloader communicating to the server 
(native or streaming way) - it is still a client to a SSL server.

Overall, either I fail to completely understand the current sstableloader 
documentation/code  OR the documentation could be better in clearly calling out 
(how Google Gemini AI search results tell the story- see the screenshot below) 
- specially focus on the #2 it says similar to what I suggest here. It is 
interesting to notice here that while the below search result have 
corresponding link for each point, actually those link don't tell the story as 
clearly as the AI result did :) )

!image-2025-05-13-23-42-19-536.png!


was (Author: maulin.vasavada):
Okay, so few more questions,
 # When you use `-f` option to specify cassandra.yaml path, are you 
inheriting/copying the same file that you use for the Cassandra service/server? 
(i.e. either you are running sstablesloader from one of the server nodes (hence 
can access the same file) OR copied the file over to a VM where you are running 
sstableloader from)
 # If you are NOT using the same file (either by sharing the location or 
copying it over) as the server's cassandra.yaml, then you must be creating a 
new/separate cassandra.yaml file just to use it for the sstableloader, correct?
 ## If this is the case, in my opinion what you specify in the 
client_encryption_options AND server_encryption_options must be the same config 
because to the Cassandra target nodes you connect with (for native transport or 
storage port) your VM is a 'client' and whatever server configured for SSL you 
need to comply with. This means if the server configured to require_client_auth 
you will need to have keystore for providing your client certs AND truststore 
to trust server cert. If the server configured required_client_auth as false 
you ONLY need a truststore to be able to trust server cert.

Now, coming to you original question/ask - That if your config file used for 
the ssltableloader tool (not the config file inherited/copying from the 
server's config) specified the `require_client_auth` false you should not 
require truststore - does not logically make sense to me. This is because as a 
client you don't control if you require the client to auth with server or not 
and as a client if you do have to use SSL (since server configured 
client_encryption_options as enabled on its side) you MUST need a truststore 
always to be able to validate server's cert.

Btw, I do agree with your code pointers that the code is using two distinct 
paths - one to use client_encryption_options from the config file (the init() 
method in the NativeSSTableLoaderClient uses those ssl options to fetch 
metadata etc) AND second to use server_encryption_options from the config file 
for the storage port connection (via
BulkLoadConnectionFactory(serverEncOptions, storagePort) ).

Also, when I think about the sstableloader options from the documentation 
standpoint ([link|#usage]]) - From the command line it ONLY has "Client SSL" 
options overrides and not server encryption options overrides - why? I think 
its because no matter how you see sstableloader communicating to the server 
(native or streaming way) - it is still a client to a SSL server.

Overall, either I fail to completely understand the current sstableloader 
documentation/code  OR the documentation could be better in clearly calling out 
(how Google Gemini AI search results tell the story- see the screenshot below) 
- specially focus on the #2 it says similar to what I suggest here.

!image-2025-05-13-23-42-19-536.png!

> Bulkloader requires truststore path even when required_client_auth is false 
> in cassandra.yaml
> ---------------------------------------------------------------------------------------------
>
>                 Key: CASSANDRA-20484
>                 URL: https://issues.apache.org/jira/browse/CASSANDRA-20484
>             Project: Apache Cassandra
>          Issue Type: Bug
>          Components: Tool/bulk load
>            Reporter: Niket Vilas Bagwe
>            Assignee: Maulin Vasavada
>            Priority: Normal
>         Attachments: image-2025-05-13-23-42-19-536.png
>
>
> If client_encryption_options are enabled in cassandra.yaml with 
> require_client_auth false *and* Sstableloader command is used with -f option 
> (for cassandra.yaml path), sstableloader fails with "NoSuchFileException: 
> conf/.truststore".
> Sample sstableloader command is as follows.
> |sstableloader /opt/cassandra/data/keyspace/table -d 127.0.0.1 -p 9042 -ssp 
> 7001 -sp 7000 -f */opt/nosql/clusters/cassandra-6382/conf/cassandra.yaml* -u 
> "caas" -pw *******|
> Exception encountered is as follows:
>  
> {code:java}
> Exception in thread "main" java.lang.RuntimeException: Could not create SSL 
> Context.
>         at 
> org.apache.cassandra.tools.BulkLoader.buildSSLOptions(BulkLoader.java:271)
>         at org.apache.cassandra.tools.BulkLoader.load(BulkLoader.java:72)
>         at org.apache.cassandra.tools.BulkLoader.main(BulkLoader.java:58)
> Caused by: javax.net.ssl.SSLException: failed to build trust manager store 
> for secure connections
>         at 
> org.apache.cassandra.security.FileBasedSslContextFactory.buildTrustManagerFactory(FileBasedSslContextFactory.java:196)
>         at 
> org.apache.cassandra.security.AbstractSslContextFactory.createJSSESslContext(AbstractSslContextFactory.java:155)
>         at 
> org.apache.cassandra.security.SSLFactory.createSSLContext(SSLFactory.java:127)
>         at 
> org.apache.cassandra.tools.BulkLoader.buildSSLOptions(BulkLoader.java:267)
>         ... 2 more
> Caused by: java.nio.file.NoSuchFileException: conf/.truststore
>         at 
> java.base/sun.nio.fs.UnixException.translateToIOException(UnixException.java:92)
>         at 
> java.base/sun.nio.fs.UnixException.rethrowAsIOException(UnixException.java:111)
>         at 
> java.base/sun.nio.fs.UnixException.rethrowAsIOException(UnixException.java:116)
>         at 
> java.base/sun.nio.fs.UnixFileSystemProvider.newByteChannel(UnixFileSystemProvider.java:219)
>         at java.base/java.nio.file.Files.newByteChannel(Files.java:371)
>         at java.base/java.nio.file.Files.newByteChannel(Files.java:422)
>         at 
> java.base/java.nio.file.spi.FileSystemProvider.newInputStream(FileSystemProvider.java:420)
>         at java.base/java.nio.file.Files.newInputStream(Files.java:156)
>         at 
> org.apache.cassandra.security.FileBasedSslContextFactory.buildTrustManagerFactory(FileBasedSslContextFactory.java:183)
>         ... 5 more {code}
> The reason for this is that sslcontext for native connection in BulkLoader is 
> always created with EncryptionOptions.ClientAuth set to true at 
> [line|https://github.com/apache/cassandra/blob/f278f6774fc76465c182041e081982105c3e7dbb/src/java/org/apache/cassandra/tools/BulkLoader.java#L267]
>  irrespective of the value of require_client_auth present in cassandra.yaml. 
> Because of this BulkLoader always expects to have a truststore file inorder 
> to verify the client certificates. Copying below the errorneous code block 
> for reference.
> {code:java}
>     private static SSLOptions buildSSLOptions(EncryptionOptions 
> clientEncryptionOptions)
>     {        if (!clientEncryptionOptions.getEnabled())
>         {
>             return null;
>         }        SSLContext sslContext;
>         try
>         {
> ################ problematic line
>             sslContext = SSLFactory.createSSLContext(clientEncryptionOptions, 
> true);
> ################
>         }
>         catch (IOException e)
>         {
>             throw new RuntimeException("Could not create SSL Context.", e);
>         } {code}
>  



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscr...@cassandra.apache.org
For additional commands, e-mail: commits-h...@cassandra.apache.org

Reply via email to