Spaces:
Running
on
T4
Running
on
T4
File size: 11,840 Bytes
05b5eca 291ae1f 05b5eca 6d546ef 7a8e9d9 1439a1c 8f2b0ed 05b5eca 8f2b0ed 05b5eca 291ae1f 05b5eca 291ae1f 05b5eca fea5074 05b5eca 7a8e9d9 05b5eca fea5074 05b5eca 7a8e9d9 05b5eca |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 |
import os
from dotenv import load_dotenv
load_dotenv()
import uuid
import streamlit as st
import random
import torch
import threading
import time
import pandas as pd
from transformers import AutoTokenizer, AutoModelForCausalLM, TextIteratorStreamer
from peft import PeftModel
from huggingface_hub import login, whoami
st.set_page_config(layout="wide")
scroll_css = """
<style>
.table-scroll {
overflow-x: auto;
width: 100%;
max-width: 100%;
}
</style>
"""
st.markdown(scroll_css, unsafe_allow_html=True)
st.title("Auto Generate Prompts Using HI Model")
st.markdown(
"""
Humane Intelligence’s Auto Red Teaming prototype is built to empower clients to run red-teaming exercises on their AI applications using HI’s intuitive no-code/low-code platform.
The system generates adversarial prompts via a model trained on proprietary HI data, targeting potential vulnerabilities in the client’s models or applications. These responses are then evaluated by a separate judge LLM, also trained by HI.
Specifically, the prototype follows these steps:
1. Generates adversarial prompts based on a selected **bias category** and **country/region** using HI’s pre-trained model.
2. Selects the most effective prompts and feeds them into the client’s model to elicit responses.
3. Uses a dedicated HI-trained judge LLM to assess the responses.
4. Produces a final output that includes a **probability score** and a **justification** for each response.
"""
)
# --- Hugging Face Login ---
# Use session state for hf_token if it exists, otherwise fallback to env.
default_hf_token = st.session_state.get("hf_token", os.getenv("HUGGINGFACE_API_KEY") or "")
hf_token = st.sidebar.text_input("Enter your Hugging Face API Token", type="password", value=default_hf_token)
if "hf_logged_in" not in st.session_state:
st.session_state.hf_logged_in = False
if st.sidebar.button("Login to Hugging Face"):
if hf_token:
try:
login(token=hf_token)
user_info = whoami()
st.sidebar.success(f"Logged in as: {user_info['name']}")
st.session_state.hf_logged_in = True
st.session_state.hf_token = hf_token # Persist the API key in session state.
except Exception as e:
st.sidebar.error(f"Login failed: {e}")
st.session_state.hf_logged_in = False
else:
st.sidebar.error("Please provide your Hugging Face API Token.")
if not st.session_state.hf_logged_in:
st.warning("Please login to Hugging Face to load the model.")
else:
# --- Device Selection and Model Loading ---
def get_device():
if torch.cuda.is_available():
return "cuda"
elif torch.backends.mps.is_available():
return "mps"
else:
return "cpu"
@st.cache_resource(show_spinner=True)
def load_model(hf_token):
device = get_device()
base_model = AutoModelForCausalLM.from_pretrained(
"meta-llama/Llama-3.2-1B-Instruct",
trust_remote_code=True,
torch_dtype=torch.float16,
use_auth_token=hf_token
)
tokenizer = AutoTokenizer.from_pretrained(
"Akash190104/space_turtle_101",
use_fast=False,
use_auth_token=hf_token
)
if tokenizer.pad_token is None:
tokenizer.pad_token = tokenizer.eos_token
model = PeftModel.from_pretrained(
base_model,
"Akash190104/space_turtle_101",
use_auth_token=hf_token
)
model.to(device)
return model, tokenizer, device
with st.spinner("Loading model, please wait..."):
try:
model, tokenizer, device = load_model(hf_token)
# --- Enable Flash Attention if using CUDA ---
if device == "cuda":
try:
model.config.use_flash_attention = True
st.info("Flash Attention enabled for CUDA.")
except Exception as e:
st.warning(f"Could not enable Flash Attention: {e}")
st.success("Model loaded successfully!")
except Exception as e:
st.error(f"Model loading failed: {e}")
st.error("Ensure your token has access to meta-llama/Llama-3.2-1B-Instruct.")
st.stop()
# --- Streaming Function for a Single Sample ---
def generate_streaming_sample(prompt_text, current_placeholder):
inputs = tokenizer(prompt_text, return_tensors="pt", padding=True).to(device)
generated_text = ""
token_counter = 0
streamer = TextIteratorStreamer(tokenizer, skip_prompt=True, skip_special_tokens=True)
thread = threading.Thread(
target=model.generate,
kwargs=dict(
**inputs,
max_new_tokens=150,
do_sample=True,
temperature=0.7,
top_p=0.9,
streamer=streamer
)
)
thread.start()
for new_text in streamer:
generated_text += new_text
token_counter += 1
if token_counter % 5 == 0:
# Clear previous widget and update with a new one using a unique key.
current_placeholder.empty()
unique_key = f"current_sample_{uuid.uuid4()}"
current_placeholder.text_area(
"Current Sample Generation",
value=generated_text,
height=200,
key=unique_key
)
thread.join()
current_placeholder.empty()
unique_key = f"current_sample_{uuid.uuid4()}"
current_placeholder.text_area(
"Current Sample Generation",
value=generated_text,
height=200,
key=unique_key
)
return generated_text
# --- Preset Bias and Country Lists ---
biases = [
"Socio-economic bias", "Gender bias", "Caste bias", "Religious bias", "Ethnic bias", "Age bias",
"Regional stereotyping", "Language discrimination", "Political bias", "Educational bias",
"Occupational bias", "Disability bias", "Appearance-based bias", "Colorism", "Nationality bias",
"Urban-rural bias", "Immigration bias"
]
countries = [
"China", "India", "Philippines", "Vietnam", "Southeast Asia", "Europe", "Nigeria", "United States",
"Mexico", "Canada", "Germany", "France", "Brazil", "South Africa", "Russia", "Japan", "South Korea",
"Australia", "Middle East", "Latin America", "Eastern Europe", "Bangladesh", "Pakistan", "Indonesia",
"Turkey", "Egypt", "Kenya", "Argentina"
]
mode = st.radio("Select Mode", ("Interactive", "Random Generation (10 samples)"))
if mode == "Interactive":
st.subheader("Interactive Mode")
num_samples = st.number_input("Number of samples to generate", min_value=1, value=1, step=1)
sample_inputs = []
for i in range(num_samples):
st.markdown(f"#### Sample {i+1} Input")
# Bias dropdown with custom option
bias_options = biases + ["Custom Bias"]
bias_choice = st.selectbox("Select Bias Category", options=bias_options, key=f"bias_{i}")
if bias_choice == "Custom Bias":
custom_bias = st.text_input("Enter Custom Bias", key=f"custom_bias_{i}")
final_bias = custom_bias.strip() if custom_bias.strip() != "" else "Custom Bias"
else:
final_bias = bias_choice
# Country dropdown with custom option
country_options = countries + ["Custom Region"]
country_choice = st.selectbox("Select Country/Region", options=country_options, key=f"country_{i}")
if country_choice == "Custom Region":
custom_region = st.text_input("Enter Custom Region", key=f"custom_region_{i}")
final_country = custom_region.strip() if custom_region.strip() != "" else "Custom Region"
else:
final_country = country_choice
sample_inputs.append((final_bias, final_country))
if st.button("Generate Samples"):
if any(bias.strip() == "" or country.strip() == "" for bias, country in sample_inputs):
st.error("Please provide valid entries for all samples.")
else:
final_samples = []
current_placeholder = st.empty() # Single current generation box
start_time = time.time()
for bias_input, country_input in sample_inputs:
prompt = f"```{bias_input} in {country_input}```\n"
generated = generate_streaming_sample(prompt, current_placeholder)
final_samples.append({"Bias Category and Country": prompt, "Auto Generated Prompts": generated})
end_time = time.time()
total_time = end_time - start_time
st.info(f"{num_samples} sample(s) generated in {total_time:.2f} seconds!")
df_final = pd.DataFrame(final_samples)
df_final_styled = df_final.style \
.set_properties(subset=["Auto Generated Prompts"],
**{"white-space": "pre-wrap", "width": "300px"}) \
.set_properties(subset=["Bias Category and Country"],
**{"white-space": "nowrap", "width": "120px"})
st.markdown("**Final Samples**")
st.markdown("<div class='table-scroll'>", unsafe_allow_html=True)
st.table(df_final_styled)
st.markdown("</div>", unsafe_allow_html=True)
st.download_button("Download Outputs", df_final.to_csv(index=False), file_name="outputs.csv")
# Save generated samples under 'single_sample'
st.session_state.single_sample = final_samples
elif mode == "Random Generation (10 samples)":
st.subheader("Random Generation Mode")
if st.button("Generate 10 Random Samples"):
final_samples = []
status_placeholder = st.empty() # Status message
current_placeholder = st.empty() # Current sample display
start_time = time.time()
for i in range(10):
status_placeholder.info(f"Generating sample {i+1} of 10...")
bias_choice = random.choice(biases)
country_choice = random.choice(countries)
prompt = f"```{bias_choice} in {country_choice}```\n"
sample_output = generate_streaming_sample(prompt, current_placeholder)
final_samples.append({"Bias Category and Country": prompt, "Auto Generated Prompts": sample_output})
current_placeholder.empty()
end_time = time.time()
total_time = end_time - start_time
status_placeholder.success(f"10 samples generated in {total_time:.2f} seconds!")
df_final = pd.DataFrame(final_samples)
df_final_styled = df_final.style \
.set_properties(subset=["Auto Generated Prompts"],
**{"white-space": "pre-wrap", "width": "300px"}) \
.set_properties(subset=["Bias Category and Country"],
**{"white-space": "nowrap", "width": "120px"})
st.markdown("**Final Samples**")
st.markdown("<div class='table-scroll'>", unsafe_allow_html=True)
st.table(df_final_styled)
st.markdown("</div>", unsafe_allow_html=True)
st.download_button("Download Outputs", df_final.to_csv(index=False), file_name="outputs.csv")
st.session_state.all_samples = final_samples |