diff options
Diffstat (limited to 'g4f')
-rw-r--r-- | g4f/Provider/Phind.py | 50 | ||||
-rw-r--r-- | g4f/models.py | 2 |
2 files changed, 49 insertions, 3 deletions
diff --git a/g4f/Provider/Phind.py b/g4f/Provider/Phind.py index e7156842..a7fdbeca 100644 --- a/g4f/Provider/Phind.py +++ b/g4f/Provider/Phind.py @@ -1,5 +1,6 @@ from __future__ import annotations +from urllib import parse from datetime import datetime from ..typing import AsyncResult, Messages @@ -55,9 +56,9 @@ class Phind(AsyncGeneratorProvider): "customLinks": [] }, "context": "\n".join([message["content"] for message in messages if message["role"] == "system"]), - "rewrittenQuestion": prompt, - "challenge": 0.21132115912208504 } + data["challenge"] = generate_challenge(data) + async with session.post(f"https://https.api.phind.com/infer/", headers=headers, json=data) as response: new_line = False async for line in response.iter_lines(): @@ -65,6 +66,8 @@ class Phind(AsyncGeneratorProvider): chunk = line[6:] if chunk.startswith(b'<PHIND_DONE/>'): break + if chunk.startswith(b'<PHIND_BACKEND_ERROR>'): + raise RuntimeError(f"Response: {chunk}") if chunk.startswith(b'<PHIND_WEBRESULTS>') or chunk.startswith(b'<PHIND_FOLLOWUP>'): pass elif chunk.startswith(b"<PHIND_METADATA>") or chunk.startswith(b"<PHIND_INDICATOR>"): @@ -78,3 +81,46 @@ class Phind(AsyncGeneratorProvider): new_line = False else: new_line = True + +def deterministic_stringify(obj): + def handle_value(value): + if isinstance(value, (dict, list)): + if isinstance(value, list): + return '[' + ','.join(sorted(map(handle_value, value))) + ']' + else: # It's a dict + return '{' + deterministic_stringify(value) + '}' + elif isinstance(value, bool): + return 'true' if value else 'false' + elif isinstance(value, (int, float)): + return format(value, '.8f').rstrip('0').rstrip('.') + elif isinstance(value, str): + return f'"{value}"' + else: + return 'null' + + items = sorted(obj.items(), key=lambda x: x[0]) + return ','.join([f'{k}:{handle_value(v)}' for k, v in items if handle_value(v) is not None]) + +def simple_hash(s): + d = 0 + for char in s: + if len(char) > 1 or ord(char) >= 256: + continue + d = ((d << 5) - d + ord(char[0])) & 0xFFFFFFFF + if d > 0x7FFFFFFF: # 2147483647 + d -= 0x100000000 # Subtract 2**32 + return d + +def generate_challenge(obj): + deterministic_str = deterministic_stringify(obj) + encoded_str = parse.quote(deterministic_str, safe='') + + c = simple_hash(encoded_str) + a = (9301 * c + 49297) + b = 233280 + + # If negativ, we need a special logic + if a < 0: + return ((a%b)-b)/b + else: + return a%b/b
\ No newline at end of file diff --git a/g4f/models.py b/g4f/models.py index e58ccef2..b971cf2d 100644 --- a/g4f/models.py +++ b/g4f/models.py @@ -89,7 +89,7 @@ gpt_4 = Model( name = 'gpt-4', base_provider = 'openai', best_provider = RetryProvider([ - Bing, Phind, Liaobots, + Bing, Liaobots, ]) ) |