11import type { Disposable } from 'vscode' ;
2+ import { window } from 'vscode' ;
23import type { Container } from '../../container' ;
34import type { GitRemote } from '../../git/models/remote' ;
45import type { RichRemoteProvider } from '../../git/remotes/richRemoteProvider' ;
6+ import { isSubscriptionPaidPlan } from '../../subscription' ;
57import { log } from '../../system/decorators/log' ;
68import { Logger } from '../../system/logger' ;
79import { getLogScope } from '../../system/logger.scope' ;
@@ -83,6 +85,8 @@ export class FocusService implements Disposable {
8385 const result = ( await rsp . json ( ) ) as Result ;
8486 return type == null ? result . data : result . data . filter ( i => i . type === type ) ;
8587 } catch ( ex ) {
88+ if ( ex instanceof Error && ex . message === 'Authentication required' ) return [ ] ;
89+
8690 Logger . error ( ex , scope ) ;
8791 debugger ;
8892 throw ex ;
@@ -104,6 +108,10 @@ export class FocusService implements Disposable {
104108 const scope = getLogScope ( ) ;
105109
106110 try {
111+ if ( ! ( await ensureAccount ( 'Pinning requires an account' , this . container ) ) ) {
112+ throw new Error ( 'Unable to pin item: account required' ) ;
113+ }
114+
107115 type Result = { data : EnrichedItemResponse } ;
108116
109117 const rq : EnrichedItemRequest = {
@@ -143,6 +151,10 @@ export class FocusService implements Disposable {
143151 const scope = getLogScope ( ) ;
144152
145153 try {
154+ if ( ! ( await ensurePaidPlan ( 'Snoozing requires a trial or paid plan' , this . container ) ) ) {
155+ throw new Error ( 'Unable to snooze item: subscription required' ) ;
156+ }
157+
146158 type Result = { data : EnrichedItemResponse } ;
147159
148160 const rq : EnrichedItemRequest = {
@@ -177,3 +189,109 @@ export class FocusService implements Disposable {
177189 return this . delete ( id , 'unsnooze' ) ;
178190 }
179191}
192+
193+ async function ensurePaidPlan ( title : string , container : Container ) : Promise < boolean > {
194+ while ( true ) {
195+ const subscription = await container . subscription . getSubscription ( ) ;
196+ if ( subscription . account ?. verified === false ) {
197+ const resend = { title : 'Resend Verification' } ;
198+ const cancel = { title : 'Cancel' , isCloseAffordance : true } ;
199+ const result = await window . showWarningMessage (
200+ `${ title } \n\nYou must verify your email before you can continue.` ,
201+ { modal : true } ,
202+ resend ,
203+ cancel ,
204+ ) ;
205+
206+ if ( result === resend ) {
207+ if ( await container . subscription . resendVerification ( ) ) {
208+ continue ;
209+ }
210+ }
211+
212+ return false ;
213+ }
214+
215+ const plan = subscription . plan . effective . id ;
216+ if ( isSubscriptionPaidPlan ( plan ) ) break ;
217+
218+ if ( subscription . account == null ) {
219+ const signIn = { title : 'Start Free GitKraken Trial' } ;
220+ const cancel = { title : 'Cancel' , isCloseAffordance : true } ;
221+ const result = await window . showWarningMessage (
222+ `${ title } \n\nTry our developer productivity and collaboration services free for 7 days.` ,
223+ { modal : true } ,
224+ signIn ,
225+ cancel ,
226+ ) ;
227+
228+ if ( result === signIn ) {
229+ if ( await container . subscription . loginOrSignUp ( ) ) {
230+ continue ;
231+ }
232+ }
233+ } else {
234+ const upgrade = { title : 'Upgrade to Pro' } ;
235+ const cancel = { title : 'Cancel' , isCloseAffordance : true } ;
236+ const result = await window . showWarningMessage (
237+ `${ title } \n\nContinue to use our developer productivity and collaboration services.` ,
238+ { modal : true } ,
239+ upgrade ,
240+ cancel ,
241+ ) ;
242+
243+ if ( result === upgrade ) {
244+ void container . subscription . purchase ( ) ;
245+ }
246+ }
247+
248+ return false ;
249+ }
250+
251+ return true ;
252+ }
253+
254+ async function ensureAccount ( title : string , container : Container ) : Promise < boolean > {
255+ while ( true ) {
256+ const subscription = await container . subscription . getSubscription ( ) ;
257+ if ( subscription . account ?. verified === false ) {
258+ const resend = { title : 'Resend Verification' } ;
259+ const cancel = { title : 'Cancel' , isCloseAffordance : true } ;
260+ const result = await window . showWarningMessage (
261+ `${ title } \n\nYou must verify your email before you can continue.` ,
262+ { modal : true } ,
263+ resend ,
264+ cancel ,
265+ ) ;
266+
267+ if ( result === resend ) {
268+ if ( await container . subscription . resendVerification ( ) ) {
269+ continue ;
270+ }
271+ }
272+
273+ return false ;
274+ }
275+
276+ if ( subscription . account != null ) break ;
277+
278+ const signIn = { title : 'Sign In / Sign Up' } ;
279+ const cancel = { title : 'Cancel' , isCloseAffordance : true } ;
280+ const result = await window . showWarningMessage (
281+ `${ title } \n\nGain access to our developer productivity and collaboration services.` ,
282+ { modal : true } ,
283+ signIn ,
284+ cancel ,
285+ ) ;
286+
287+ if ( result === signIn ) {
288+ if ( await container . subscription . loginOrSignUp ( ) ) {
289+ continue ;
290+ }
291+ }
292+
293+ return false ;
294+ }
295+
296+ return true ;
297+ }
0 commit comments