@@ -19,6 +19,7 @@ import { expect, use } from 'chai';
19
19
import sinonChai from 'sinon-chai' ;
20
20
import chaiAsPromised from 'chai-as-promised' ;
21
21
import { ChromeAdapter } from './chrome-adapter' ;
22
+ import { stub } from 'sinon' ;
22
23
23
24
use ( sinonChai ) ;
24
25
use ( chaiAsPromised ) ;
@@ -41,13 +42,13 @@ describe('ChromeAdapter', () => {
41
42
} ) ;
42
43
} ) ;
43
44
describe ( 'isAvailable' , ( ) => {
44
- it ( 'returns true if a model is available' , async ( ) => {
45
+ it ( 'returns true if model is readily available' , async ( ) => {
45
46
const aiProvider = {
46
47
languageModel : {
47
48
capabilities : ( ) =>
48
49
Promise . resolve ( {
49
50
available : 'readily'
50
- } as AILanguageModelCapabilities )
51
+ } )
51
52
}
52
53
} as AI ;
53
54
const adapter = new ChromeAdapter ( aiProvider , 'prefer_on_device' ) ;
@@ -57,5 +58,94 @@ describe('ChromeAdapter', () => {
57
58
} )
58
59
) . to . be . true ;
59
60
} ) ;
61
+ it ( 'returns false and triggers download when model is available after download' , async ( ) => {
62
+ const aiProvider = {
63
+ languageModel : {
64
+ capabilities : ( ) =>
65
+ Promise . resolve ( {
66
+ available : 'after-download'
67
+ } ) ,
68
+ create : ( ) => Promise . resolve ( { } )
69
+ }
70
+ } as AI ;
71
+ const createStub = stub ( aiProvider . languageModel , 'create' ) . resolves (
72
+ { } as AILanguageModel
73
+ ) ;
74
+ const adapter = new ChromeAdapter ( aiProvider , 'prefer_on_device' ) ;
75
+ expect (
76
+ await adapter . isAvailable ( {
77
+ contents : [ { role : 'user' , parts : [ { text : 'hi' } ] } ]
78
+ } )
79
+ ) . to . be . false ;
80
+ expect ( createStub ) . to . have . been . calledOnce ;
81
+ } ) ;
82
+ it ( 'avoids redundant downloads' , async ( ) => {
83
+ const aiProvider = {
84
+ languageModel : {
85
+ capabilities : ( ) =>
86
+ Promise . resolve ( {
87
+ available : 'after-download'
88
+ } ) ,
89
+ create : ( ) => { }
90
+ }
91
+ } as AI ;
92
+ const downloadPromise = new Promise < AILanguageModel > ( ( ) => {
93
+ /* never resolves */
94
+ } ) ;
95
+ const createStub = stub ( aiProvider . languageModel , 'create' ) . returns (
96
+ downloadPromise
97
+ ) ;
98
+ const adapter = new ChromeAdapter ( aiProvider ) ;
99
+ await adapter . isAvailable ( {
100
+ contents : [ { role : 'user' , parts : [ { text : 'hi' } ] } ]
101
+ } ) ;
102
+ await adapter . isAvailable ( {
103
+ contents : [ { role : 'user' , parts : [ { text : 'hi' } ] } ]
104
+ } ) ;
105
+ expect ( createStub ) . to . have . been . calledOnce ;
106
+ } ) ;
107
+ it ( 'clears state when download completes' , async ( ) => {
108
+ const aiProvider = {
109
+ languageModel : {
110
+ capabilities : ( ) =>
111
+ Promise . resolve ( {
112
+ available : 'after-download'
113
+ } ) ,
114
+ create : ( ) => { }
115
+ }
116
+ } as AI ;
117
+ let resolveDownload ;
118
+ const downloadPromise = new Promise < AILanguageModel > ( resolveCallback => {
119
+ resolveDownload = resolveCallback ;
120
+ } ) ;
121
+ const createStub = stub ( aiProvider . languageModel , 'create' ) . returns (
122
+ downloadPromise
123
+ ) ;
124
+ const adapter = new ChromeAdapter ( aiProvider ) ;
125
+ await adapter . isAvailable ( {
126
+ contents : [ { role : 'user' , parts : [ { text : 'hi' } ] } ]
127
+ } ) ;
128
+ resolveDownload ! ( ) ;
129
+ await adapter . isAvailable ( {
130
+ contents : [ { role : 'user' , parts : [ { text : 'hi' } ] } ]
131
+ } ) ;
132
+ expect ( createStub ) . to . have . been . calledTwice ;
133
+ } ) ;
134
+ it ( 'returns false when model is never available' , async ( ) => {
135
+ const aiProvider = {
136
+ languageModel : {
137
+ capabilities : ( ) =>
138
+ Promise . resolve ( {
139
+ available : 'no'
140
+ } )
141
+ }
142
+ } as AI ;
143
+ const adapter = new ChromeAdapter ( aiProvider , 'prefer_on_device' ) ;
144
+ expect (
145
+ await adapter . isAvailable ( {
146
+ contents : [ { role : 'user' , parts : [ { text : 'hi' } ] } ]
147
+ } )
148
+ ) . to . be . false ;
149
+ } ) ;
60
150
} ) ;
61
151
} ) ;
0 commit comments