3rd party CA problems/Questions

I am starting to work through the 3rd party CA process.

I have looked at Creating Endpoint with your own Certificate Authority - #11 by dovholuknf and watched the video, though I am not sure where to proceed.

Outcome (end goal): Use a Windows CA for auto client enrollment, as Windows can take care of (re)-enrolling client certificates using group policy.

So,
a. I created a new CA through the ZAC - this seemed to go well.
b. NOTE: When adding a CA through the GUI, can it jump into asking for the verification certificate as that is what it is expecting next, This will also show the user that this is what is logically next to be completed.
c. I have verified the certificate authority

Wheels now fell off.
I need to download a jwt token for the CA. Why can I not download this through the GUI? ie, when you have a list of the CA, have an option saying ā€œDownload the JWTā€ file (along with Edit and Delete)? It is my understanding that this file is static for a 3rd party CA. This is where I am currently stuck.

What I have done:
Run the following command to find the id of CA (again not in the GUI anywhere)

ziti@5b8dcc17f2a1:/openziti$ ziti edge list cas
id: tYKkaXdfJ    name: WindowsCA   token:     identityRoles: [#test]    flags: [VAE]    identityNameFormat: [caName]-[commonName]    fingerprint: ad8e...6c
results: 1-1 of 1

Flags: (V) Verified, (A) AutoCa Enrollment, (O) OttCA Enrollment, (E) Authentication Enabled

This is how it looks:

I am running this through the docker-compose example, so from the docker-ziti-controller-1 container I do the following

ziti@5b8dcc17f2a1:/openziti$ edge_controller_uri="https://ziti-edge-controller:1280"
ziti@5b8dcc17f2a1:/openziti$ zt_session=$(curl -sk -H "Content-Type: application/json" \
    ${edge_controller_uri}/authenticate?method=password \
    -d "{\"username\":\"admin\",\"password\":\"admin\"}" | \
    jq -r .data.token)
ziti@5b8dcc17f2a1:/openziti$ echo $zt_session
7e236eea-2486-4495-af9b-1cef7827f817
ziti@5b8dcc17f2a1:/openziti$ curl -sk -H "Content-Type: application/json" \
             -H "zt-session: ${zt_session}" \
             "${edge_controller_uri}/cas"
{"error":{"cause":{"code":"UNHANDLED","message":"path /edge/client/v1/cas was not found"},"code":"NOT_FOUND","message":"The resource requested was not found or is no longer available","requestId":"EeNwUd6LKC"},"meta":{"apiEnrollmentVersion":"0.0.1","apiVersion":"0.0.1"}}

So I am having a difficulty getting the jwt.

Other questions
a) So I set this up with docker compose, which would have created itā€™s own CA. All the edge components etc will be using this PKI. I have now added a third party CA (Well, kind of have). Will this impact connecting identities with one CA, and infrastructure with another? I would assume not, as they will all know about different all the CAs?

b) ZEDW - it appears that you I might need to export the machine/user certificate from the windows certificate store to be able to use it in ZEDW (ie, out of the OS native cert store, into the client cert store). Is it a possibility to have ZEDW when prompting for an ID, to list/detail the certs in the MACHINE/MY store and/or the USER/My store to use that information, along with a ā€œHave fileā€ option. Ideally the client should be able to interface with the local certificate stores? This way, when WIndows updates the certs, the client should see/use this change.

c) By the looks, identities need to be configured with [caname]-[identityname]. Can this be changed? Not sure how this will work with Windows auto-enrollment certs which are just machine or username based.

Some of these items will hopefully be able to answer when I can (easily) get the jwt token.

You will find some awesome content here.

Woah! Neat goal!!!!! I'm interested in learning how you do that. I'm a "Windows person" but I've never seen this side of Windows so you're bound to teach me something. You're also making some great progress and you have a lot of questions here. It'll take me a bit to chug through them all your questions. I'll reply but it'll take me a while. I'll follow up soon.

1 Like

Finally getting around to responding to you, @gooseleggs, thanks for being patient,

I do hate it when the wheels fall off! :frowning: sorry about that. I filed an issue to download the jwt for an 'auto enrollment enabled CA' from ZAC here Expose "auto" jwt from ZAC Ā· Issue #35 Ā· openziti/ziti-console Ā· GitHub. This file is necessary when doing the enrollment process. Looking at a sample jwt, it's really just got the controller URL baked into it but since the JWT is a signed document, you need to get it from the controller (which has signed the document).

Your URL is wrong there. Maybe our doc is stale again. We did an "API split" a few months ago and changed the way these endpoints work. The proper URL is: "https://${ZITI_EDGE_CTRL_ADVERTISED}/edge/management/v1/cas". The video you reference has all the commands I ran in the description. You should be able to lift what you need from there. (it's where I got the URL mentioned above)

Nope. When your client connects, it presents a certificate. If the certificate is valid, your identity will get a session id allowing it to connect to edge routers. Once connected, the identity would still need to be authorized for services, but it's that initial connection that 3rd party CAs is controlling, not the authorization. So, should be fine.

At this time - no, it's not a feature that has been worked on yet. If you have a certificate you'd like to use, you're going to need to be able to export the cert and the key into a file which the CSDK can use. The file format is pretty obvious, you can find them in %windir%\System32\config\systemprofile\AppData\Roaming\NetFoundry. We haven't integrated with the Windows certificate store yet and I'm not sure where that might sit on a priority timeline for it getting done by the people currently working on the project. If you have a request, please file it as a github issue with as much details as you can add to the issue so that if/when we get around to implementing it we'll have a nice baseline idea of what to do and where to start.

I expect that it can be changed but I'm pretty sure the functionality is going to be limited to a PUT to the REST API (not exposed in ZAC yet). Do you have a format that you would like to see instead?

Cheers

That is called the identity name format. For CA's the default identity name format is [caName]-[commonName] inside the controller. The default identity name format is used when no value is set during auto enrollment.

Identity name formats can be created with any custom string you want and also support the following replacement strings (bracketed by []):

  • caName - the name of the 3rd Party CA inside of Ziti
  • caId - the id of the 3rd party CA inside of Ziti
  • commonName - the common name presented by the client certificate
  • requestedName - the name sent during the enrollment request from the client
  • identityId - the id of the identity created during auto enrollment

Example: "test1-[caName]-[commonName]"

The default identity name format can be updated via the CLI or directly through the Edge Management API.

Example: ziti edge update ca <nameOrId> --identity-name-format "my-name-format"

As a note, names in Ziti are unique. Thus, during auto enrollment if a name collision occurs an ever increasing number is appended to the identity name to work through the problem. This approach is used because there tends to be no human around to assist the process.

Just getting back to this now

Yes - it is. Have a look here ( Ziti Identities | Ziti (openziti.github.io)) and it references the old location. I am working through the Auto-Enrollment option, however this is not going to fly for a Windows CA, as you cannot export the user/computer certificates by default when created by auto-enrollment (by design, nor should you). However, since in a test environment, I have having a play to see how it goes by creating exportable certificates (not auto enrolled).

I think for the auto-enrollment, the JWT I am after is this URL: ${edge_controller_uri}/edge/management/v1/cas/uyNxYNehxA (where uyNxYNehxA is the ID of the CA) and I do get a JWT, however it is not encoded?. What I am getting back is this - should it look like this? ...

{"data":{"_links":{"self":{"href":"./cas/uyNxYNehxA"}},"createdAt":"2022-06-26T06:21:31.431Z","id":"uyNxYNehxA","tags":{},"updatedAt":"2022-06-26T10:56:54.453Z","certPem":"-----BEGIN CERTIFICATE-----\nMIIDjzCCAnegAwIBAgIQVsVwi9ZJMLlOuffxko2MXDANBgkqhkiG9w0BAQsFADBO\nMRQwEgYKCZImiZPyLGQBGRYEdGVzdDEYMBYGCgmSJomT8ixkARkWCGludGVybmFs\nMRwwGgYDVQQDExNpbnRlcm5hbC1URVNULUFELUNBMB4XDTIyMDYwODEwNDMwOVoX\nDTI3MDYwODEwNTMwNlowTjEUMBIGCgmSJomT8ixkARkWBHRlc3QxGDAWBgoJkiaJ\nk/IsZAEZFghpbnRlcm5hbDEcMBoGA1UEAxMTaW50ZXJuYWwtVEVTVC1BRC1DQTCC\nASIwDQYJKoZIhvcNAQEBBQADggEPADCCAQoCggEBAKoJEfly9loLFdLxkRWt5gsi\nLptDHxKV8bJN/HpR0BXQ/CjNLGFdEBjMv8axMQxb18Q/P/LJRxoBk0JO9hqYqayN\nl45MNBLWPMB06bwq7F/AI/gPYeAwNnWvSGg5OO1UO+vyrPAaklm2foUwccN5FUhM\nBqEQYetnjo4FyrR0X3bkYTfUNUlTtQOOaRmqaCDQYpd4fyM3DFU1O3ZnTbPc49Rf\nnpP2R1+/n02Vu+65Ay0OQkLid0FkmT/netqRZO1q7HZABY/5NxR5JmhZsnXRMvg9\nZIM+HTsh1i6ibkNjn2TA1ntA/m5drFHC76YrBXD4ccmC4pnk2T6rWvenDac8b8MC\nAwEAAaNpMGcwEwYJKwYBBAGCNxQCBAYeBABDAEEwDgYDVR0PAQH/BAQDAgGGMA8G\nA1UdEwEB/wQFMAMBAf8wHQYDVR0OBBYEFKDr7H2XAkAwxHK1VEGzKCVyPO+PMBAG\nCSsGAQQBgjcVAQQDAgEAMA0GCSqGSIb3DQEBCwUAA4IBAQBvfrw7t3FtPXjS2/pp\nJxipcsY4g8KZwNkalgYtvF6UB0Cdr75i/pKrdZmhhe9fRqO8c0ibPg+U4aO+iQnr\ntPy+K634tO2+NuhU6zsGqsjVKtFQOvCrA/WtKZTxgkMUg+tvCJTFvBOEPzbn0sj0\n972Atjm5SXVphPdETmBKDjr9GUAR007n1xORxCP9m80EYltUxlzUJ7VdANiu+KBR\nEatBHJ4zlIFi1tLFrQ0OOTQGRdVwWAViiVG54PrclprnsfT7igVoz6UjbOUmbVGN\nTAsLZC3dm0FarGE8iLslB0fCATMOItT/UHl2lbm7odscer/+cF+cytUjJN5/Tvio\nYUc/\n-----END CERTIFICATE-----","fingerprint":"ad8ed869e9c463f7c1b9572824d5f4a9f88f346c","identityNameFormat":"[caName]-[commonName]","identityRoles":null,"isAuthEnabled":false,"isAutoCaEnrollmentEnabled":false,"isOttCaEnrollmentEnabled":true,"isVerified":true,"name":"WindowsCA","verificationToken":"JyNPYNehx"},"meta":{}}

I am after a bit of clarification as well please. In your video, you created the identity on the controller, and configured it for auto-enrollment (OTT), so when you started the edgecontroller using that identity the world was happy, and it auto-enrolled and away it went. However...

In the description here: Ziti Identities | Ziti (openziti.github.io) (auto-enrollment) it talks like the clients has all the certificates and Ziti knows nothing about them (in fact it talks about not having to do anything in the controller except authorize them after the id is created). Then, under the enrolling section, it talks about using the ziti cli to enroll the client, but there is no ziti cli on the windows client (actually there is, c:
windows\installer{9ddd4554...}\ziti.cli although it says it is not for x64 systems). Just wondering how I might enroll a client with a certificate from the client itself? I would need the crt, key and jwt. I would gather it will be an API request?

Thinking about this from a windows silent install perspective (haven't got to this bit yet).

a) Silent install of ziti software
b) Pull a certificate from the Windows CA using Windows magic
c) Enroll the Ziti client into the controller with a supplied JWT as part of the install.

(I would probably flip it, and get it to enroll as an OTT somehow, but since it appears I should be able to do this, I am pulling the thread....)

I am still working through this as time permits. I have had some more success. Now I just need a push in the right direction. I have

a) Loaded up a 3rd party CA
b) Verified the 3rd party CA
c) Created a 3rd party certificate that is on the client machine
d) downloaded the JWT token to enroll said 3rd party certificate

I am trying to achieve the 3rd party Autoenroll configuration. Now, I have run ziti edge enroll --cert cert.pem --key server.key --jwt autoenroll.jwt --out id.json and that does enroll the identity into ZAC - Yippeeā€¦

However, I want to enroll the certificate (identity) into ZEDW and have it loaded, and that is where I get stuck. I cannot see a command to load the id.json file into ZEDW, either through the GUI, or preferably through the command line.

If I drop the ziti.exe line, and replace it with

c:\Program Files (x86)\NetFoundry, Inc\Ziti Desktop Edge>"c:\Program Files (x86)\NetFoundry, Inc\Ziti Desktop Edge\ziti-edge-tunnel.exe" enroll --cert cert.pem --key server.key --jwt autoenroll.jwt

I get StartServiceCtrlDispatcher failed (1063) and goes no further. I looked at the instructions on the video, and you start the ziti-edge-tunnel from the command line and pass the json through the command line. However I have a running ZEDW that I want to add the .json or enroll through the command line into ZEDW

What mistake have I done?

1 Like

:confused: there's no good way to "import an identity" through the UI like this right now. You can import it, but you need to be admin to the machine because ZDEW runs under the system account. You can copy that json file directly into %windir%\system32\config\systemprofile\AppData\Roaming\NetFoundry and stop/start ZDEW. When it comes back online/starts up it scans for 'orphaned' identities. The new identity will be discovered and will be loaded on startup.

I am concerned there might be a bug in the enroll function of ziti-edge-tunnel though. You might need to use the regular ziti cli to do the enrollment if that's the case.

I'll add another enhancement request for this but realistically "moving/importing" an identity is generally a bad idea because the json file has your OpenZiti identity inside it. We do have a 3rd party CA issue already to make supporting these sorts of identities easier it's not ready yet and won't be for a while. Support 3rd Party CA Ā· Issue #468 Ā· openziti/desktop-edge-win Ā· GitHub

1 Like

If you wanted to do this for a Macā€¦ where would the identity json files be located?

Iā€™m not the expert on Mac but Iā€™m pretty sure you cannot do this for a Mac. The identity is stored in the keychain.

1 Like

makes senseā€¦ I will investigate that further.