From e5b7f72b719814ffa2748e8e8ed1c6713a24e1a6 Mon Sep 17 00:00:00 2001 From: Heiner Lohaus Date: Thu, 22 Feb 2024 00:16:58 +0100 Subject: Move some modules, create providers dir Set min version for duckduckgo Make duckduckgo search async Remove get_lastet_version --- g4f/client.py | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-) (limited to 'g4f/client.py') diff --git a/g4f/client.py b/g4f/client.py index a1494d47..4e5394b7 100644 --- a/g4f/client.py +++ b/g4f/client.py @@ -1,12 +1,14 @@ from __future__ import annotations import re +import os from .stubs import ChatCompletion, ChatCompletionChunk, Image, ImagesResponse from .typing import Union, Generator, Messages, ImageType -from .base_provider import BaseProvider, ProviderType +from .providers.types import BaseProvider, ProviderType from .image import ImageResponse as ImageProviderResponse -from .Provider import BingCreateImages, Gemini, OpenaiChat +from .Provider.BingCreateImages import BingCreateImages +from .Provider.needs_auth import Gemini, OpenaiChat from .errors import NoImageResponseError from . import get_model_and_provider @@ -43,7 +45,7 @@ def iter_response( yield ChatCompletionChunk(last_chunk, finish_reason) content += str(chunk) if max_tokens is not None and idx + 1 >= max_tokens: - finish_reason = "max_tokens" + finish_reason = "length" first = -1 word = None if stop is not None: @@ -69,7 +71,7 @@ def iter_response( if not stream: if response_format is not None and "type" in response_format: if response_format["type"] == "json_object": - response = read_json(response) + content = read_json(content) yield ChatCompletion(content, finish_reason) class Client(): @@ -89,13 +91,14 @@ class Client(): self.proxies: Proxies = proxies def get_proxy(self) -> Union[str, None]: - if isinstance(self.proxies, str) or self.proxies is None: + if isinstance(self.proxies, str): return self.proxies + elif self.proxies is None: + return os.environ.get("G4F_PROXY") elif "all" in self.proxies: return self.proxies["all"] elif "https" in self.proxies: return self.proxies["https"] - return None class Completions(): def __init__(self, client: Client, provider: ProviderType = None): @@ -123,7 +126,7 @@ class Completions(): stream, **kwargs ) - response = provider.create_completion(model, messages, stream=stream, **kwargs) + response = provider.create_completion(model, messages, stream=stream, proxy=self.client.get_proxy(), **kwargs) stop = [stop] if isinstance(stop, str) else stop response = iter_response(response, stream, response_format, max_tokens, stop) return response if stream else next(response) -- cgit v1.2.3 From 74397096b794631e718e7e5dfc7ed8517d0e42c2 Mon Sep 17 00:00:00 2001 From: Heiner Lohaus Date: Fri, 23 Feb 2024 02:35:13 +0100 Subject: Use new client in inter api --- g4f/client.py | 37 ++++++++++++++++++++++++------------- 1 file changed, 24 insertions(+), 13 deletions(-) (limited to 'g4f/client.py') diff --git a/g4f/client.py b/g4f/client.py index 4e5394b7..b44a5230 100644 --- a/g4f/client.py +++ b/g4f/client.py @@ -2,6 +2,9 @@ from __future__ import annotations import re import os +import time +import random +import string from .stubs import ChatCompletion, ChatCompletionChunk, Image, ImagesResponse from .typing import Union, Generator, Messages, ImageType @@ -10,10 +13,11 @@ from .image import ImageResponse as ImageProviderResponse from .Provider.BingCreateImages import BingCreateImages from .Provider.needs_auth import Gemini, OpenaiChat from .errors import NoImageResponseError -from . import get_model_and_provider +from . import get_model_and_provider, get_last_provider ImageProvider = Union[BaseProvider, object] Proxies = Union[dict, str] +IterResponse = Generator[ChatCompletion | ChatCompletionChunk, None, None] def read_json(text: str) -> dict: """ @@ -31,18 +35,16 @@ def read_json(text: str) -> dict: return text def iter_response( - response: iter, + response: iter[str], stream: bool, response_format: dict = None, max_tokens: int = None, stop: list = None -) -> Generator: +) -> IterResponse: content = "" finish_reason = None - last_chunk = None + completion_id = ''.join(random.choices(string.ascii_letters + string.digits, k=28)) for idx, chunk in enumerate(response): - if last_chunk is not None: - yield ChatCompletionChunk(last_chunk, finish_reason) content += str(chunk) if max_tokens is not None and idx + 1 >= max_tokens: finish_reason = "length" @@ -63,16 +65,25 @@ def iter_response( if first != -1: finish_reason = "stop" if stream: - last_chunk = chunk + yield ChatCompletionChunk(chunk, None, completion_id, int(time.time())) if finish_reason is not None: break - if last_chunk is not None: - yield ChatCompletionChunk(last_chunk, finish_reason) - if not stream: + finish_reason = "stop" if finish_reason is None else finish_reason + if stream: + yield ChatCompletionChunk(None, finish_reason, completion_id, int(time.time())) + else: if response_format is not None and "type" in response_format: if response_format["type"] == "json_object": content = read_json(content) - yield ChatCompletion(content, finish_reason) + yield ChatCompletion(content, finish_reason, completion_id, int(time.time())) + +def iter_append_model_and_provider(response: IterResponse) -> IterResponse: + last_provider = None + for chunk in response: + last_provider = get_last_provider(True) if last_provider is None else last_provider + chunk.model = last_provider.get("model") + chunk.provider = last_provider.get("name") + yield chunk class Client(): proxies: Proxies = None @@ -113,7 +124,7 @@ class Completions(): stream: bool = False, response_format: dict = None, max_tokens: int = None, - stop: Union[list. str] = None, + stop: list[str] | str = None, **kwargs ) -> Union[ChatCompletion, Generator[ChatCompletionChunk]]: if max_tokens is not None: @@ -128,7 +139,7 @@ class Completions(): ) response = provider.create_completion(model, messages, stream=stream, proxy=self.client.get_proxy(), **kwargs) stop = [stop] if isinstance(stop, str) else stop - response = iter_response(response, stream, response_format, max_tokens, stop) + response = iter_append_model_and_provider(iter_response(response, stream, response_format, max_tokens, stop)) return response if stream else next(response) class Chat(): -- cgit v1.2.3 From d733930a2b1876340039d90f19ece81fab0d078d Mon Sep 17 00:00:00 2001 From: Heiner Lohaus Date: Fri, 23 Feb 2024 02:51:10 +0100 Subject: Fix unittests, use Union typing --- g4f/client.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'g4f/client.py') diff --git a/g4f/client.py b/g4f/client.py index b44a5230..023d53f6 100644 --- a/g4f/client.py +++ b/g4f/client.py @@ -17,7 +17,7 @@ from . import get_model_and_provider, get_last_provider ImageProvider = Union[BaseProvider, object] Proxies = Union[dict, str] -IterResponse = Generator[ChatCompletion | ChatCompletionChunk, None, None] +IterResponse = Generator[Union[ChatCompletion, ChatCompletionChunk], None, None] def read_json(text: str) -> dict: """ @@ -124,7 +124,7 @@ class Completions(): stream: bool = False, response_format: dict = None, max_tokens: int = None, - stop: list[str] | str = None, + stop: Union[list[str], str] = None, **kwargs ) -> Union[ChatCompletion, Generator[ChatCompletionChunk]]: if max_tokens is not None: -- cgit v1.2.3