| from __future__ import annotations |
|
|
| import os |
| import threading |
|
|
| os.environ.setdefault("OPENBLAS_NUM_THREADS", "4") |
| os.environ.setdefault("OMP_NUM_THREADS", "4") |
| os.environ.setdefault("MKL_NUM_THREADS", "4") |
| os.environ.setdefault("TOKENIZERS_PARALLELISM", "false") |
| os.environ.setdefault("GRADIO_SSR_MODE", "false") |
|
|
| import gradio as gr |
| import spaces |
| import torch |
| from transformers import AutoModelForCausalLM, AutoTokenizer, TextIteratorStreamer |
|
|
| MODEL_ID = os.environ.get("TINY_AYA_MODEL", "CohereLabs/tiny-aya-global") |
| DEFAULT_MAX_TOKENS = int(os.environ.get("TINY_AYA_MAX_TOKENS", "400")) |
|
|
| tokenizer = AutoTokenizer.from_pretrained(MODEL_ID) |
| model = AutoModelForCausalLM.from_pretrained(MODEL_ID, torch_dtype="auto") |
| if torch.cuda.is_available(): |
| model.to("cuda") |
| model.eval() |
|
|
| _lock = threading.Lock() |
|
|
|
|
| def _messages(system: str, user: str): |
| messages = [] |
| if system and system.strip(): |
| messages.append({"role": "system", "content": system.strip()}) |
| messages.append({"role": "user", "content": (user or "").strip()}) |
| return messages |
|
|
|
|
| @spaces.GPU(duration=120) |
| def generate(system: str, user: str, max_tokens: int = DEFAULT_MAX_TOKENS, temperature: float = 0.8): |
| if not user or not user.strip(): |
| raise gr.Error("user prompt required") |
| max_tokens = max(1, min(int(max_tokens or DEFAULT_MAX_TOKENS), 1024)) |
| temperature = max(0.0, min(float(temperature if temperature is not None else 0.8), 2.0)) |
| inputs = tokenizer.apply_chat_template( |
| _messages(system, user), |
| tokenize=True, |
| add_generation_prompt=True, |
| return_dict=True, |
| return_tensors="pt", |
| ).to(model.device) |
| with _lock, torch.inference_mode(): |
| outputs = model.generate( |
| **inputs, |
| max_new_tokens=max_tokens, |
| do_sample=temperature > 0, |
| temperature=max(temperature, 1e-5), |
| top_p=0.95, |
| pad_token_id=tokenizer.eos_token_id, |
| ) |
| return tokenizer.decode(outputs[0][inputs["input_ids"].shape[-1]:], skip_special_tokens=True).strip() |
|
|
|
|
| @spaces.GPU(duration=120) |
| def generate_stream(system: str, user: str, max_tokens: int = DEFAULT_MAX_TOKENS, temperature: float = 0.8): |
| if not user or not user.strip(): |
| raise gr.Error("user prompt required") |
| max_tokens = max(1, min(int(max_tokens or DEFAULT_MAX_TOKENS), 1024)) |
| temperature = max(0.0, min(float(temperature if temperature is not None else 0.8), 2.0)) |
| inputs = tokenizer.apply_chat_template( |
| _messages(system, user), |
| tokenize=True, |
| add_generation_prompt=True, |
| return_dict=True, |
| return_tensors="pt", |
| ).to(model.device) |
| streamer = TextIteratorStreamer(tokenizer, skip_prompt=True, skip_special_tokens=True) |
|
|
| def run(): |
| with _lock, torch.inference_mode(): |
| model.generate( |
| **inputs, |
| max_new_tokens=max_tokens, |
| do_sample=temperature > 0, |
| temperature=max(temperature, 1e-5), |
| top_p=0.95, |
| pad_token_id=tokenizer.eos_token_id, |
| streamer=streamer, |
| ) |
|
|
| thread = threading.Thread(target=run, daemon=True) |
| thread.start() |
| acc = "" |
| for token in streamer: |
| acc += token |
| yield acc |
| thread.join(timeout=1) |
|
|
|
|
| with gr.Blocks(title="Tiny Army Tiny Aya ZeroGPU") as demo: |
| gr.Markdown("# Tiny Army Tiny Aya ZeroGPU") |
| system = gr.Textbox(label="System", lines=5) |
| user = gr.Textbox(label="User", lines=5) |
| max_tokens = gr.Slider(1, 1024, value=DEFAULT_MAX_TOKENS, step=1, label="Max new tokens") |
| temperature = gr.Slider(0, 2, value=0.8, step=0.05, label="Temperature") |
| btn = gr.Button("Generate") |
| out = gr.Textbox(label="Output", lines=10) |
| btn.click(generate, inputs=[system, user, max_tokens, temperature], outputs=out, api_name="generate") |
| btn.click(generate_stream, inputs=[system, user, max_tokens, temperature], outputs=out, api_name="generate_stream") |
|
|
|
|
| if __name__ == "__main__": |
| demo.launch() |
|
|