Skip to content

Commit

Permalink
Merge pull request #2463 from hlohaus/neww
Browse files Browse the repository at this point in the history
Add Authentication Setup Guide
  • Loading branch information
hlohaus authored Dec 7, 2024
2 parents 4f57392 + 486190d commit 0cb9ed0
Show file tree
Hide file tree
Showing 23 changed files with 392 additions and 153 deletions.
10 changes: 7 additions & 3 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -107,7 +107,7 @@ docker run \
hlohaus789/g4f:latest-slim \
rm -r -f /app/g4f/ \
&& pip install -U g4f[slim] \
&& python -m g4f.cli api --gui --debug
&& python -m g4f --debug
```
It also updates the `g4f` package at startup and installs any new required dependencies.

Expand All @@ -134,7 +134,7 @@ By following these steps, you should be able to successfully install and run the

Run the **Webview UI** on other Platforms:

- [/docs/guides/webview](docs/webview.md)
- [/docs/webview](docs/webview.md)

##### Use your smartphone:

Expand Down Expand Up @@ -204,7 +204,7 @@ image_url = response.data[0].url
print(f"Generated image URL: {image_url}")
```

[![Image with cat](/docs/cat.jpeg)](docs/client.md)
[![Image with cat](/docs/images/cat.jpeg)](docs/client.md)

#### **Full Documentation for Python API**
- **New:**
Expand Down Expand Up @@ -241,6 +241,10 @@ This API is designed for straightforward implementation and enhanced compatibili

### Configuration

#### Authentication

Refer to the [G4F Authentication Setup Guide](docs/authentication.md) for detailed instructions on setting up authentication.

#### Cookies

Cookies are essential for using Meta AI and Microsoft Designer to create images.
Expand Down
2 changes: 1 addition & 1 deletion docs/async_client.md
Original file line number Diff line number Diff line change
Expand Up @@ -145,7 +145,7 @@ async def main():
provider=g4f.Provider.CopilotAccount
)

image = requests.get("https://raw.githubusercontent.com/xtekky/gpt4free/refs/heads/main/docs/cat.jpeg", stream=True).raw
image = requests.get("https://raw.githubusercontent.com/xtekky/gpt4free/refs/heads/main/docs/images/cat.jpeg", stream=True).raw

response = await client.chat.completions.create(
model=g4f.models.default,
Expand Down
139 changes: 139 additions & 0 deletions docs/authentication.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,139 @@
# G4F Authentication Setup Guide

This documentation explains how to set up Basic Authentication for the GUI and API key authentication for the API when running the G4F server.

## Prerequisites

Before proceeding, ensure you have the following installed:
- Python 3.x
- G4F package installed (ensure it is set up and working)
- Basic knowledge of using environment variables on your operating system

## Steps to Set Up Authentication

### 1. API Key Authentication for Both GUI and API

To secure both the GUI and the API, you'll authenticate using an API key. The API key should be injected via an environment variable and passed to both the GUI (via Basic Authentication) and the API.

#### Steps to Inject the API Key Using Environment Variables:

1. **Set the environment variable** for your API key:

On Linux/macOS:
```bash
export G4F_API_KEY="your-api-key-here"
```

On Windows (Command Prompt):
```bash
set G4F_API_KEY="your-api-key-here"
```

On Windows (PowerShell):
```bash
$env:G4F_API_KEY="your-api-key-here"
```

Replace `your-api-key-here` with your actual API key.

2. **Run the G4F server with the API key injected**:

Use the following command to start the G4F server. The API key will be passed to both the GUI and the API:

```bash
python -m g4f --debug --port 8080 --g4f-api-key $G4F_API_KEY
```

- `--debug` enables debug mode for more verbose logs.
- `--port 8080` specifies the port on which the server will run (you can change this if needed).
- `--g4f-api-key` specifies the API key for both the GUI and the API.

#### Example:

```bash
export G4F_API_KEY="my-secret-api-key"
python -m g4f --debug --port 8080 --g4f-api-key $G4F_API_KEY
```

Now, both the GUI and API will require the correct API key for access.

---

### 2. Accessing the GUI with Basic Authentication

The GUI uses **Basic Authentication**, where the **username** can be any value, and the **password** is your API key.

#### Example:

To access the GUI, open your web browser and navigate to `http://localhost:8080/chat/`. You will be prompted for a username and password.

- **Username**: You can use any username (e.g., `user` or `admin`).
- **Password**: Enter your API key (the same key you set in the `G4F_API_KEY` environment variable).

---

### 3. Python Example for Accessing the API

To interact with the API, you can send requests by including the `g4f-api-key` in the headers. Here's an example of how to do this using the `requests` library in Python.

#### Example Code to Send a Request:

```python
import requests

url = "http://localhost:8080/v1/chat/completions"

# Body of the request
body = {
"model": "your-model-name", # Replace with your model name
"provider": "your-provider", # Replace with the provider name
"messages": [
{
"role": "user",
"content": "Hello"
}
]
}

# API Key (can be set as an environment variable)
api_key = "your-api-key-here" # Replace with your actual API key

# Send the POST request
response = requests.post(url, json=body, headers={"g4f-api-key": api_key})

# Check the response
print(response.status_code)
print(response.json())
```

In this example:
- Replace `"your-api-key-here"` with your actual API key.
- `"model"` and `"provider"` should be replaced with the appropriate model and provider you're using.
- The `messages` array contains the conversation you want to send to the API.

#### Response:

The response will contain the output of the API request, such as the model's completion or other relevant data, which you can then process in your application.

---

### 4. Testing the Setup

- **Accessing the GUI**: Open a web browser and navigate to `http://localhost:8080/chat/`. The GUI will now prompt you for a username and password. You can enter any username (e.g., `admin`), and for the password, enter the API key you set up in the environment variable.

- **Accessing the API**: Use the Python code example above to send requests to the API. Ensure the correct API key is included in the `g4f-api-key` header.

---

### 5. Troubleshooting

- **GUI Access Issues**: If you're unable to access the GUI, ensure that you are using the correct API key as the password.
- **API Access Issues**: If the API is rejecting requests, verify that the `G4F_API_KEY` environment variable is correctly set and passed to the server. You can also check the server logs for more detailed error messages.

---

## Summary

By following the steps above, you will have successfully set up Basic Authentication for the G4F GUI (using any username and the API key as the password) and API key authentication for the API. This ensures that only authorized users can access both the interface and make API requests.

[Return to Home](/)
4 changes: 2 additions & 2 deletions docs/client.md
Original file line number Diff line number Diff line change
Expand Up @@ -181,7 +181,7 @@ client = Client(
)

response = client.images.create_variation(
image=open("cat.jpg", "rb"),
image=open("docs/images/cat.jpg", "rb"),
model="dall-e-3",
# Add any other necessary parameters
)
Expand Down Expand Up @@ -235,7 +235,7 @@ client = Client(
)

image = requests.get("https://raw.githubusercontent.com/xtekky/gpt4free/refs/heads/main/docs/cat.jpeg", stream=True).raw
# Or: image = open("docs/cat.jpeg", "rb")
# Or: image = open("docs/images/cat.jpeg", "rb")

response = client.chat.completions.create(
model=g4f.models.default,
Expand Down
File renamed without changes
File renamed without changes.
File renamed without changes
7 changes: 4 additions & 3 deletions g4f/Provider/Blackbox2.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,14 +6,15 @@

from ..typing import AsyncResult, Messages
from .base_provider import AsyncGeneratorProvider, ProviderModelMixin
from .. import debug

class Blackbox2(AsyncGeneratorProvider, ProviderModelMixin):
url = "https://www.blackbox.ai"
api_endpoint = "https://www.blackbox.ai/api/improve-prompt"
working = True
supports_system_message = True
supports_message_history = True

supports_stream = False
default_model = 'llama-3.1-70b'
models = [default_model]

Expand Down Expand Up @@ -62,8 +63,8 @@ async def create_async_generator(
raise KeyError("'prompt' key not found in the response")
except Exception as e:
if attempt == max_retries - 1:
yield f"Error after {max_retries} attempts: {str(e)}"
raise RuntimeError(f"Error after {max_retries} attempts: {str(e)}")
else:
wait_time = delay * (2 ** attempt) + random.uniform(0, 1)
print(f"Attempt {attempt + 1} failed. Retrying in {wait_time:.2f} seconds...")
debug.log(f"Attempt {attempt + 1} failed. Retrying in {wait_time:.2f} seconds...")
await asyncio.sleep(wait_time)
44 changes: 18 additions & 26 deletions g4f/Provider/needs_auth/Gemini.py
Original file line number Diff line number Diff line change
Expand Up @@ -76,9 +76,8 @@ async def nodriver_login(cls, proxy: str = None) -> AsyncIterator[str]:
page = await browser.get(f"{cls.url}/app")
await page.select("div.ql-editor.textarea", 240)
cookies = {}
for c in await page.browser.cookies.get_all():
if c.domain.endswith(".google.com"):
cookies[c.name] = c.value
for c in await page.send(nodriver.cdp.network.get_cookies([cls.url])):
cookies[c.name] = c.value
await page.close()
cls._cookies = cookies

Expand All @@ -92,7 +91,6 @@ async def create_async_generator(
connector: BaseConnector = None,
image: ImageType = None,
image_name: str = None,
response_format: str = None,
return_conversation: bool = False,
conversation: Conversation = None,
language: str = "en",
Expand All @@ -113,7 +111,7 @@ async def create_async_generator(
async for chunk in cls.nodriver_login(proxy):
yield chunk
except Exception as e:
raise MissingAuthError('Missing "__Secure-1PSID" cookie', e)
raise MissingAuthError('Missing or invalid "__Secure-1PSID" cookie', e)
if not cls._snlm0e:
if cls._cookies is None or "__Secure-1PSID" not in cls._cookies:
raise MissingAuthError('Missing "__Secure-1PSID" cookie')
Expand Down Expand Up @@ -153,7 +151,7 @@ async def create_async_generator(
) as response:
await raise_for_status(response)
image_prompt = response_part = None
last_content_len = 0
last_content = ""
async for line in response.content:
try:
try:
Expand All @@ -171,32 +169,26 @@ async def create_async_generator(
yield Conversation(response_part[1][0], response_part[1][1], response_part[4][0][0])
content = response_part[4][0][1][0]
except (ValueError, KeyError, TypeError, IndexError) as e:
print(f"{cls.__name__}:{e.__class__.__name__}:{e}")
debug.log(f"{cls.__name__}:{e.__class__.__name__}:{e}")
continue
match = re.search(r'\[Imagen of (.*?)\]', content)
if match:
image_prompt = match.group(1)
content = content.replace(match.group(0), '')
yield content[last_content_len:]
last_content_len = len(content)
if image_prompt:
try:
images = [image[0][3][3] for image in response_part[4][0][12][7][0]]
if response_format == "b64_json":
pattern = r"http://googleusercontent.com/image_generation_content/\d+"
content = re.sub(pattern, "", content)
if last_content and content.startswith(last_content):
yield content[len(last_content):]
else:
yield content
last_content = content
if image_prompt:
try:
images = [image[0][3][3] for image in response_part[4][0][12][7][0]]
image_prompt = image_prompt.replace("a fake image", "")
yield ImageResponse(images, image_prompt, {"cookies": cls._cookies})
else:
resolved_images = []
preview = []
for image in images:
async with client.get(image, allow_redirects=False) as fetch:
image = fetch.headers["location"]
async with client.get(image, allow_redirects=False) as fetch:
image = fetch.headers["location"]
resolved_images.append(image)
preview.append(image.replace('=s512', '=s200'))
yield ImageResponse(resolved_images, image_prompt, {"orginal_links": images, "preview": preview})
except TypeError:
pass
except TypeError:
pass

@classmethod
async def synthesize(cls, params: dict, proxy: str = None) -> AsyncIterator[bytes]:
Expand Down
6 changes: 5 additions & 1 deletion g4f/Provider/needs_auth/OpenaiAccount.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,4 +5,8 @@
class OpenaiAccount(OpenaiChat):
needs_auth = True
parent = "OpenaiChat"
image_models = ["dall-e"]
image_models = ["dall-e-3", "gpt-4", "gpt-4o"]
default_vision_model = "gpt-4o"
default_image_model = "dall-e-3"
models = [*OpenaiChat.fallback_models, default_image_model]
model_aliases = {default_image_model: default_vision_model}
Loading

0 comments on commit 0cb9ed0

Please sign in to comment.