Skip to content

Conversation

@costrouc
Copy link
Contributor

@costrouc costrouc commented Oct 28, 2025

Moved to a branch within the repository to run tests so closed PR #715

Intent

Prior to recent changes on the Snowflake side, proxied authentication headers carried enough information for Connect running in Snowflake SPCS to identify users. With the move to OIDC, Connect servers no longer trust Snowflake headers for username identification. This requires users to provide both a Snowflake connection (for proxied authentication) and a Connect API key (for OIDC authentication).

This commit is how we will be performing authentication within the Snowflake Posit Team Native Application. This will serve as a good example of how it can be supported in the rsconnect* packages. Posit Connect supports alternate headers for authorization https://docs.posit.co/connect/admin/authentication/proxied/#api-use.

I think this PR also highlights the importance of OIDC device flow authentication which is supported in PPM
https://packagemanager.rstudio.com/__docs__/admin/appendix//cli/rspm_login_sso.html which would again eliminate the need for an api key which this PR reintroduces for SPCS.

Example

(.venv) costrouc@puffin:~/p/posit-dev/rsconnect-python$ rsconnect add --server https://abcdefghijklmnop-org-account.snowflakecomputing.app/ --snowflake-connection-name myconnection --name dev-test --api-key X8iPx.....ZVPxSk
Checking Posit Connect (SPCS) credential...      [OK]
Updated Posit Connect (SPCS) credential "dev-test".

Type of Change

  • Bug Fix
  • New Feature
  • Breaking Change (this changes how SPCS rsconnect authentication is performed)

Approach

Automated Tests

Directions for Reviewers

Checklist

  • I have updated CHANGELOG.md to cover notable changes.
  • I have updated all related GitHub issues to reflect their current state.

costrouc and others added 3 commits October 23, 2025 23:36
This commit is mainly meant as an example to complement changes in how
we will be performing authentication within the Snowflake Posit Team
Native Application. When / if that PR of work for OIDC goes through
this will serve as a good example of how it can be supported.

I think this PR also highlights the importance of OIDC device flow
authentication which is supported in PPM
https://packagemanager.rstudio.com/__docs__/admin/appendix//cli/rspm_login_sso.html
which would again eliminate the need for an api key.

I REALLY like how this package uses the snow command to generate the
jwt used for snowflake ingress as this means our Posit libraries don't
have to re-implement the snowflake authentication.

Going to put this PR in draft and will contribute more after I share
this with our team tomorrow at Standup.
This commit refines the Snowflake SPCS (Snowpark Container Services)
OIDC authentication implementation to better align with existing
codebase patterns and improve type safety.

Changes:
- Make SPCSConnectServer.api_key Optional[str] to match RSConnectServer
- Add comprehensive docstring to SPCSConnectServer class explaining
  SPCS deployment and authentication approach
- Reorder RSConnectExecutor server type detection to check for
  snowflake_connection_name first, as SPCS is more specific than
  generic Connect deployment
- Ensure api_key is passed to SPCSConnectServer in all instantiations
  (RSConnectExecutor.__init__ and validate_spcs_server)
- Add null check before setting X-RSC-Authorization header to fix
  type checking error
- Update all test cases in SPCSConnectServerTestCase to pass api_key
  parameter and verify it's set correctly

All SPCS-specific tests pass. The implementation now follows the
established patterns for server authentication while maintaining
backward compatibility.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
Add changelog entry documenting the fix for Snowflake SPCS
authentication to properly handle API keys and align with
codebase patterns.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
@github-actions
Copy link

github-actions bot commented Oct 28, 2025

PR Preview Action v1.6.2

🚀 View preview at
https://posit-dev.github.io/rsconnect-python/pr-preview/pr-717/

Built to branch gh-pages at 2025-10-28 18:16 UTC.
Preview will be ready when the GitHub Pages deployment is complete.

@github-actions
Copy link

☂️ Python Coverage

current status: ✅

Overall Coverage

Lines Covered Coverage Threshold Status
5154 3999 78% 0% 🟢

New Files

No new covered files...

Modified Files

File Coverage Status
rsconnect/api.py 77% 🟢
rsconnect/main.py 69% 🟢
TOTAL 73% 🟢

updated for commit: f06b8ee by action🐍

Copy link
Collaborator

@aronatkins aronatkins left a comment

Choose a reason for hiding this comment

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

Additional changes needed:

if api_key:
target_data = dict(api_key=api_key, insecure=insecure, ca_cert=ca_data)
elif snowflake_connection_name:
target_data = dict(snowflake_connection_name=snowflake_connection_name)
elif account_name:
target_data = dict(account_name=account_name, token=token, secret=secret)
else:
target_data = dict(token=token, secret=secret)

@aronatkins
Copy link
Collaborator

Additional changes needed:

real_server_spcs = api.SPCSConnectServer(server, api_key, snowflake_connection_name)
_test_spcs_creds(real_server_spcs)
server_store.set(name, server, snowflake_connection_name=snowflake_connection_name)
if old_server:
click.echo('Updated {} credential "{}".'.format(real_server_spcs.remote_name, name))
else:
click.echo('Added {} credential "{}".'.format(real_server_spcs.remote_name, name))

@aronatkins
Copy link
Collaborator

Both changes have been made and I have been able to successfully deploy to SPCS-hosted Connect using a saved server configuration.

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants