返回提交历史
Modified
.gitignore
+2
-0
Modified
g4f/Provider/needs_auth/OpenaiChat.py
+3
-0
Modified
g4f/providers/retry_provider.py
+72
-42
XFEstudio/gpt4free
update retryprovider
now works with one provider.
f57af704
代码差异
3 个文件
+77
-42
@@ -58,3 +58,5 @@ hardir
58
58
node_modules
59
59
models
60
60
projects/windows/g4f
61
doc.txt
62
dist.py
@@ -334,6 +334,7 @@ class OpenaiChat(AsyncGeneratorProvider, ProviderModelMixin):
334
334
Raises:
335
335
RuntimeError: If an error occurs during processing.
336
336
"""
337
337
338
async with StreamSession(
338
339
proxies={"all": proxy},
339
340
impersonate="chrome",
@@ -359,6 +360,7 @@ class OpenaiChat(AsyncGeneratorProvider, ProviderModelMixin):
359
360
if debug.logging:
360
361
print("OpenaiChat: Load default_model failed")
361
362
print(f"{e.__class__.__name__}: {e}")
363
362
364
363
365
arkose_token = None
364
366
if cls.default_model is None:
@@ -582,6 +584,7 @@ this.fetch = async (url, options) => {
582
584
user_data_dir = user_config_dir("g4f-nodriver")
583
585
except:
584
586
user_data_dir = None
587
585
588
browser = await uc.start(user_data_dir=user_data_dir)
586
589
page = await browser.get("https://chat.openai.com/")
587
590
while await page.query_selector("#prompt-textarea") is None:
@@ -12,46 +12,40 @@ class RetryProvider(BaseRetryProvider):
12
12
def __init__(
13
13
self,
14
14
providers: List[Type[BaseProvider]],
15
shuffle: bool = True
15
shuffle: bool = True,
16
single_provider_retry: bool = False,
17
max_retries: int = 3,
16
18
) -> None:
17
19
"""
18
20
Initialize the BaseRetryProvider.
19
20
21
Args:
21
22
providers (List[Type[BaseProvider]]): List of providers to use.
22
23
shuffle (bool): Whether to shuffle the providers list.
24
single_provider_retry (bool): Whether to retry a single provider if it fails.
25
max_retries (int): Maximum number of retries for a single provider.
23
26
"""
24
27
self.providers = providers
25
28
self.shuffle = shuffle
29
self.single_provider_retry = single_provider_retry
30
self.max_retries = max_retries
26
31
self.working = True
27
32
self.last_provider: Type[BaseProvider] = None
28
33
29
"""
30
A provider class to handle retries for creating completions with different providers.
31
32
Attributes:
33
providers (list): A list of provider instances.
34
shuffle (bool): A flag indicating whether to shuffle providers before use.
35
last_provider (BaseProvider): The last provider that was used.
36
"""
37
34
def create_completion(
38
35
self,
39
36
model: str,
40
37
messages: Messages,
41
38
stream: bool = False,
42
**kwargs
39
**kwargs,
43
40
) -> CreateResult:
44
41
"""
45
42
Create a completion using available providers, with an option to stream the response.
46
47
43
Args:
48
44
model (str): The model to be used for completion.
49
45
messages (Messages): The messages to be used for generating completion.
50
46
stream (bool, optional): Flag to indicate if the response should be streamed. Defaults to False.
51
52
47
Yields:
53
48
CreateResult: Tokens or results from the completion.
54
55
49
Raises:
56
50
Exception: Any exception encountered during the completion process.
57
51
"""
@@ -61,22 +55,42 @@ class RetryProvider(BaseRetryProvider):
61
55
62
56
exceptions = {}
63
57
started: bool = False
64
for provider in providers:
58
59
if self.single_provider_retry and len(providers) == 1:
60
provider = providers[0]
65
61
self.last_provider = provider
66
try:
67
if debug.logging:
68
print(f"Using {provider.__name__} provider")
69
for token in provider.create_completion(model, messages, stream, **kwargs):
70
yield token
62
for attempt in range(self.max_retries):
63
try:
64
if debug.logging:
65
print(f"Using {provider.__name__} provider (attempt {attempt + 1})")
66
for token in provider.create_completion(model, messages, stream, **kwargs):
67
yield token
71
68
started = True
72
if started:
73
return
74
except Exception as e:
75
exceptions[provider.__name__] = e
76
if debug.logging:
77
print(f"{provider.__name__}: {e.__class__.__name__}: {e}")
78
if started:
79
raise e
69
if started:
70
return
71
except Exception as e:
72
exceptions[provider.__name__] = e
73
if debug.logging:
74
print(f"{provider.__name__}: {e.__class__.__name__}: {e}")
75
if started:
76
raise e
77
else:
78
for provider in providers:
79
self.last_provider = provider
80
try:
81
if debug.logging:
82
print(f"Using {provider.__name__} provider")
83
for token in provider.create_completion(model, messages, stream, **kwargs):
84
yield token
85
started = True
86
if started:
87
return
88
except Exception as e:
89
exceptions[provider.__name__] = e
90
if debug.logging:
91
print(f"{provider.__name__}: {e.__class__.__name__}: {e}")
92
if started:
93
raise e
80
94
81
95
raise_exceptions(exceptions)
82
96
@@ -84,18 +98,15 @@ class RetryProvider(BaseRetryProvider):
84
98
self,
85
99
model: str,
86
100
messages: Messages,
87
**kwargs
101
**kwargs,
88
102
) -> str:
89
103
"""
90
104
Asynchronously create a completion using available providers.
91
92
105
Args:
93
106
model (str): The model to be used for completion.
94
107
messages (Messages): The messages to be used for generating completion.
95
96
108
Returns:
97
109
str: The result of the asynchronous completion.
98
99
110
Raises:
100
111
Exception: Any exception encountered during the asynchronous completion process.
101
112
"""
@@ -104,17 +115,36 @@ class RetryProvider(BaseRetryProvider):
104
115
random.shuffle(providers)
105
116
106
117
exceptions = {}
107
for provider in providers:
118
119
if self.single_provider_retry and len(providers) == 1:
120
provider = providers[0]
108
121
self.last_provider = provider
109
try:
110
return await asyncio.wait_for(
111
provider.create_async(model, messages, **kwargs),
112
timeout=kwargs.get("timeout", 60)
113
)
114
except Exception as e:
115
exceptions[provider.__name__] = e
116
if debug.logging:
117
print(f"{provider.__name__}: {e.__class__.__name__}: {e}")
122
for attempt in range(self.max_retries):
123
try:
124
if debug.logging:
125
print(f"Using {provider.__name__} provider (attempt {attempt + 1})")
126
return await asyncio.wait_for(
127
provider.create_async(model, messages, **kwargs),
128
timeout=kwargs.get("timeout", 60),
129
)
130
except Exception as e:
131
exceptions[provider.__name__] = e
132
if debug.logging:
133
print(f"{provider.__name__}: {e.__class__.__name__}: {e}")
134
else:
135
for provider in providers:
136
self.last_provider = provider
137
try:
138
if debug.logging:
139
print(f"Using {provider.__name__} provider")
140
return await asyncio.wait_for(
141
provider.create_async(model, messages, **kwargs),
142
timeout=kwargs.get("timeout", 60),
143
)
144
except Exception as e:
145
exceptions[provider.__name__] = e
146
if debug.logging:
147
print(f"{provider.__name__}: {e.__class__.__name__}: {e}")
118
148
119
149
raise_exceptions(exceptions)
120
150