@@ -21,9 +21,12 @@ import { getAnyAuthSession } from './session';
2121//Flag if we've shown message about broken oauth token.
2222let shown401Message = false ;
2323
24- /** Workspace PATs cannot be exchanged for a Copilot token; device OAuth is required. */
25- function isWorkspacePersonalAccessToken ( token : string ) : boolean {
26- return token . startsWith ( 'ghp_' ) || token . startsWith ( 'github_pat_' ) ;
24+ const CHE_WORKSPACE_PAT_SCOPE = 'che:workspace-pat' ;
25+
26+ /** Sessions hydrated from a workspace PAT carry the che:workspace-pat marker scope. */
27+ function isWorkspacePatSession ( session : { accessToken : string ; scopes : readonly string [ ] } ) : boolean {
28+ return session . scopes ?. includes ( CHE_WORKSPACE_PAT_SCOPE ) ||
29+ session . accessToken . startsWith ( 'ghp_' ) || session . accessToken . startsWith ( 'github_pat_' ) ;
2730}
2831
2932export class NotSignedUpError extends Error { }
@@ -83,8 +86,8 @@ export class VSCodeCopilotTokenManager extends BaseCopilotTokenManager {
8386 return { kind : 'failure' , reason : 'GitHubLoginFailed' } ;
8487 }
8588 if ( session ) {
86- if ( isWorkspacePersonalAccessToken ( session . accessToken ) ) {
87- this . _logService . info ( 'Copilot token exchange skipped (workspace PAT cannot be used for Copilot ; device authentication is required)' ) ;
89+ if ( isWorkspacePatSession ( session ) ) {
90+ this . _logService . info ( 'Copilot token exchange skipped (workspace PAT session detected via scope marker ; device authentication is required)' ) ;
8891 this . _telemetryService . sendGHTelemetryErrorEvent ( 'auth.github_login_failed' ) ;
8992 return { kind : 'failure' , reason : 'GitHubLoginFailed' } ;
9093 }
@@ -94,7 +97,7 @@ export class VSCodeCopilotTokenManager extends BaseCopilotTokenManager {
9497 if ( tokenResult . kind === 'success' ) {
9598 this . _logService . info ( `Got Copilot token for ${ session . account . label } ` ) ;
9699 this . _logService . info ( `Copilot Chat: ${ this . _envService . getVersion ( ) } , VS Code: ${ this . _envService . vscodeVersion } ` ) ;
97- } else if ( tokenResult . kind === 'failure' && ( tokenResult . reason === 'ParseFailed' || tokenResult . reason === 'RequestFailed' ) ) {
100+ } else if ( tokenResult . kind === 'failure' && ( tokenResult . reason === 'ParseFailed' || tokenResult . reason === 'RequestFailed' || tokenResult . reason === 'NotAuthorized' ) ) {
98101 this . _logService . info ( 'Copilot token exchange failed (workspace token cannot be exchanged for Copilot token), triggering sign-in flow' ) ;
99102 return { kind : 'failure' , reason : 'GitHubLoginFailed' } ;
100103 }
0 commit comments