Skip to content

feat: the option to expect a certain TLS error for the TCP monitor#6587

Merged
CommanderStorm merged 8 commits intolouislam:masterfrom
MkDev11:tls-monitor-type
Jan 6, 2026
Merged

feat: the option to expect a certain TLS error for the TCP monitor#6587
CommanderStorm merged 8 commits intolouislam:masterfrom
MkDev11:tls-monitor-type

Conversation

@MkDev11
Copy link
Contributor

@MkDev11 MkDev11 commented Jan 5, 2026

feat: add TLS monitor type for mTLS endpoint monitoring

Summary

Adds a new TLS monitor type that allows monitoring mTLS endpoints to verify they properly reject connections without client certificates.

Closes #5837

Features

  • New TLS monitor type with hostname and port configuration
  • Expected TLS Alert dropdown to specify which TLS alert to expect
  • Support for certificate_required (116) alert for mTLS verification
  • Optional certificate expiry monitoring when connection succeeds
  • Ignore TLS errors option

Use Case

Users can now:

  1. Monitor TLS endpoints and verify successful connections
  2. Verify mTLS endpoints properly reject connections without client certificates by expecting specific TLS alerts (e.g., certificate_required)
  3. Optionally monitor certificate expiration when connection succeeds

Files Changed

File Description
server/monitor-types/tls.js New TLS monitor type implementation
server/uptime-kuma-server.js Register TLS monitor type
server/server.js Save handler for expected_tls_alert field
server/model/monitor.js Add expectedTlsAlert to toJSON
src/pages/EditMonitor.vue Frontend UI for TLS monitor configuration
src/lang/en.json English translations
db/knex_migrations/2026-01-05-0000-add-tls-monitor.js Database migration

Screenshots

To be added after testing

Checklist

  • Linting passes (npm run lint)
  • Tests pass (npm test)
  • Translations added to en.json only
  • Database migration included
  • Follows existing code patterns
  • Screenshots added (pending)

Testing Instructions

  1. Run npm ci to install dependencies
  2. Run npm run dev to start dev server
  3. Create a new monitor with type "TLS"
  4. Configure hostname, port, and expected TLS alert
  5. For mTLS testing, select "certificate_required" to verify the server rejects unauthenticated connections

Contribution by Gittensor, see my contribution statistics at https://gittensor.io/miners/details?githubId=94194147

@MkDev11
Copy link
Contributor Author

MkDev11 commented Jan 5, 2026

Hi @louislam @CommanderStorm! 👋

Happy New Year 2026! 🎉🎊 Wishing you and the Uptime Kuma community a wonderful year ahead filled with success and great contributions!

I'd really appreciate it if you could take a look when you have a moment. Please let me know if there are any changes needed or if you have any feedback!

Thank you for maintaining such an amazing project! 🙏

@CommanderStorm
Copy link
Collaborator

how does it differ form the current tcp monitor?

@CommanderStorm CommanderStorm added the question Further information is requested label Jan 5, 2026
@CommanderStorm CommanderStorm marked this pull request as draft January 5, 2026 19:26
@MkDev11
Copy link
Contributor Author

MkDev11 commented Jan 5, 2026

form the current tcp monitor?

Hi @CommanderStorm! Great question! 👋

Key Differences from TCP Monitor

The main difference is the expected behavior on failure:

TCP Monitor (existing)

  • ✅ UP = Connection succeeds
  • ❌ DOWN = Connection fails (any error)

TLS Monitor (new)

  • ✅ UP = Specific TLS alert received (e.g., certificate_required)
  • ❌ DOWN = Wrong alert or unexpected success

Use Case: mTLS Verification

For mTLS endpoints, you want to verify the server correctly rejects connections without a client certificate. With the TCP monitor:

Server rejects connection → TCP shows DOWN ❌ (but this is actually correct behavior!)

With the TLS monitor:

Server returns "certificate_required" alert → TLS shows UP ✅ (server is correctly enforcing mTLS)
Server accepts connection without cert → TLS shows DOWN ❌ (security misconfiguration!)

Why Not Extend TCP Monitor?

  1. Different semantics: TCP monitor expects success = UP. TLS monitor can expect failure = UP.
  2. TLS-specific features: Parsing TLS alert codes (RFC 5246/8446), mapping alert numbers to names.
  3. Cleaner UX: Users selecting "TLS" monitor type immediately understand it's for TLS/mTLS testing.

Summary

Feature TCP Monitor TLS Monitor
Success = UP ✅ (optional)
Specific TLS alert = UP
Parse TLS alert codes
mTLS rejection testing

Let me know if you'd like me to make any changes or if you have other questions!

@CommanderStorm
Copy link
Collaborator

CommanderStorm commented Jan 5, 2026

Since TCP already supports TLS, introducing a separate “TLS monitor” needs a very clear justification.

Please explain briefly what cannot be implemented in the existing TCP monitor without breaking its semantics or UX.

To be explicit about expectations:

  • AI tools are fine for mechanical tasks such as translation or spelling/grammar fixes.
  • They are not acceptable for design discussions, architectural justification, or review responses.

For those, I need human-written answers that demonstrate direct understanding of this codebase. Generic or AI-style responses undermine trust and make maintenance harder.

If you want to continue this discussion, please respond concisely and in your own words.

@MkDev11
Copy link
Contributor Author

MkDev11 commented Jan 6, 2026

Since TCP already supports TLS, introducing a separate “TLS monitor” needs a very clear justification.

Please explain briefly what cannot be implemented in the existing TCP monitor without breaking its semantics or UX.

To be explicit about expectations: – AI tools are fine for mechanical tasks such as translation or spelling/grammar fixes. – They are not acceptable for design discussions, architectural justification, or review responses.

For those, I need human-written answers that demonstrate direct understanding of this codebase. Generic or AI-style responses undermine trust and make maintenance harder.

If you want to continue this discussion, please respond concisely and in your own words.

@CommanderStorm, thanks for the feedback. I'll try to explain my thinking.

The main issue is that TCP monitor's logic is "connection works = UP". But for mTLS verification, I actually want the connection to fail in a specific way - that's the success case.

Let me give a concrete example: I have an mTLS endpoint that should reject anyone without a client certificate. With TCP monitor, if the server rejects me (which is correct behavior), it shows as DOWN. But that's actually what I want to happen - the server is working correctly by rejecting me.

So I need something that says "if the server returns a certificate_required TLS alert, that means it's properly configured and should be UP." That's basically the opposite of what TCP does.

I looked at adding this to TCP, but it felt wrong. TCP is straightforward - "can I reach this port?" Adding "but sometimes failure is success" logic would make it confusing for existing users. Plus I'd need to add TLS alert parsing code that doesn't really belong there.

I'm open to other approaches though. If you think there's a cleaner way to handle this within TCP (maybe a checkbox like "expect TLS rejection"?), I'm happy to try that instead. Just let me know what you'd prefer.

@CommanderStorm
Copy link
Collaborator

I think adding it to TLS makes sense since there we already have some code for TLS.
Not much, but some.

In general, I don't want two extremely close monitors due to bugs and things.

@CommanderStorm
Copy link
Collaborator

A checkbox in the UI sounds resonable for this

@MkDev11
Copy link
Contributor Author

MkDev11 commented Jan 6, 2026

@CommanderStorm Thanks for the feedback! I've refactored the PR to integrate the TLS alert checking directly into the TCP monitor instead of creating a separate monitor type.

Now there's just a dropdown in the TCP monitor settings called "Expected TLS Alert" - if you pick something like certificate_required, the monitor will mark it as UP when the server rejects the connection with that specific alert. Otherwise it works exactly like before.

This keeps everything in one place and avoids the duplicate monitor type issue you mentioned. Let me know if this approach works better or if you'd like any changes.

Copy link
Collaborator

@CommanderStorm CommanderStorm left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nice work!

Code looks very solid and mergable to me, but I would like a short sanitiy-check from @shanto on this one, if possible 😉

@MkDev11
Copy link
Contributor Author

MkDev11 commented Jan 6, 2026

@CommanderStorm Please have a look at the updates and let me know your feedback.

Copy link
Collaborator

@CommanderStorm CommanderStorm left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM from the code perspecitve, as said.

I would really like to have testcases for this. Does not have to be a long testcase, just verifying basic functionality (similarly how the existing testcase works).

Also, could you comment on the TLS_ALERT_CODES question that I had (this is not a quesion if this should be changed, more of a why you chose to do it like this)

Add a new TLS monitor type that allows monitoring mTLS endpoints to verify
they properly reject connections without client certificates.

Features:
- New TLS monitor type with hostname and port configuration
- Expected TLS Alert dropdown to specify which TLS alert to expect
- Support for certificate_required (116) alert for mTLS verification
- Optional certificate expiry monitoring when connection succeeds
- Ignore TLS errors option

Closes louislam#5837
Per CommanderStorm's feedback, instead of creating a separate TLS monitor
type, add the TLS alert checking functionality directly to the existing
TCP monitor.

Changes:
- Add TLS_ALERT_CODES, parseTlsAlertNumber(), getTlsAlertName() to tcp.js
- Add checkTlsAlert() method to TCPMonitorType for mTLS verification
- Add 'Expected TLS Alert' dropdown to TCP monitor UI
- Remove separate TLS monitor type (tls.js)

This allows users to verify mTLS endpoints reject connections without
client certificates by expecting specific TLS alerts like
'certificate_required'.

Closes louislam#5837
- Use i18n-t for description with code tag and RFC 8446 spec link
- Add comment that TLS alert names are from spec (not translatable)
- Refactor TCP monitor into smaller functions:
  - checkTcp() for standard TCP connectivity check
  - performStartTls() for STARTTLS handshake
  - checkTlsCertificate() for TLS certificate validation
  - attemptTlsConnection() for TLS connection with alert capture
- Improve error messages with more context
Error messages could be translated, but TLS alert names (e.g., certificate_required)
are from RFC 8446 spec and should remain in English for consistency.
- Test rejection when expecting TLS alert but connection succeeds
- Test UP status when expected TLS alert is received
- Test rejection when different TLS alert is received than expected
…ernal servers

- Replace client.badssl.com tests with unit tests for parseTlsAlertNumber and getTlsAlertName
- Export helper functions for testing
- Keep one integration test for connection success scenario
External services like smtp.gmail.com and xmpp.earth can be unreliable
in CI environments. Added retry logic (up to 3 attempts) to prevent
false test failures due to network issues.
@MkDev11
Copy link
Contributor Author

MkDev11 commented Jan 6, 2026

@CommanderStorm please review the update and let me know your feedback

@MkDev11 MkDev11 marked this pull request as ready for review January 6, 2026 18:39
Copy link
Collaborator

@CommanderStorm CommanderStorm left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM, thank you ❤️

@CommanderStorm CommanderStorm changed the title feat: add TLS monitor type for mTLS endpoint monitoring feat: the option to expect a certain TLS error for the TCP monitor Jan 6, 2026
@CommanderStorm CommanderStorm added this to the 2.1.0 milestone Jan 6, 2026
@CommanderStorm CommanderStorm merged commit adec2a7 into louislam:master Jan 6, 2026
23 checks passed
@shanto
Copy link
Contributor

shanto commented Jan 6, 2026

Looks like we are missing a positive test case.

Also, while what has been done (added) doesn't harm, I have a feeling that the same result could be achieved with less code and UI changes because we will almost always care about the certificate_required and nothing else. Other cases are synonymous to DOWN.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

question Further information is requested

Projects

None yet

Development

Successfully merging this pull request may close these issues.

allow monitoring mTLS endpoints to ensure rejection without cert and acception with cert

3 participants