KG0101 commited on
Commit
deca1bc
1 Parent(s): 02be256

Update app.py

Browse files
Files changed (1) hide show
  1. app.py +87 -38
app.py CHANGED
@@ -1,20 +1,24 @@
1
  import spaces
2
  import torch
3
  import gradio as gr
4
- from transformers import pipeline
5
- from llama_cpp import Llama
 
 
6
 
7
  MODEL_NAME = "openai/whisper-large-v3-turbo"
8
  BATCH_SIZE = 8
9
  FILE_LIMIT_MB = 1000
 
10
 
11
  device = 0 if torch.cuda.is_available() else "cpu"
12
 
13
- # Load the Llama model directly from Hugging Face
14
- llm = Llama.from_pretrained(
15
- repo_id="MaziyarPanahi/Qwen2-7B-Instruct-GGUF",
16
- filename="Qwen2-7B-Instruct.Q4_K_M.gguf"
17
- )
 
18
 
19
  # Initialize the transcription pipeline
20
  pipe = pipeline(
@@ -24,19 +28,6 @@ pipe = pipeline(
24
  device=device,
25
  )
26
 
27
- # Prompt for SOAP note generation
28
- sys_prompt = "You are a world class clinical assistant."
29
- task_prompt = """
30
- Convert the following transcribed conversation into a clinical SOAP note.
31
- The text includes dialogue between a physician and a patient. Please clearly distinguish between the physician's and the patient's statements.
32
- Extract and organize the information into the relevant sections of a SOAP note:
33
- - Subjective (symptoms and patient statements),
34
- - Objective (clinical findings and observations, these might be missing if the physician has not conducted a physical exam or has not verbally stated findings),
35
- - Assessment (diagnosis or potential diagnoses, objectively provide a top 5 most likely diagnosis based on just the subjective findings, and use the objective findings if available),
36
- - Plan (treatment and follow-up).
37
- Ensure the note is concise, clear, and accurately reflects the conversation.
38
- """
39
-
40
  # Function to transcribe audio inputs
41
  @spaces.GPU
42
  def transcribe(inputs, task):
@@ -45,25 +36,69 @@ def transcribe(inputs, task):
45
  text = pipe(inputs, batch_size=BATCH_SIZE, generate_kwargs={"task": task}, return_timestamps=True)["text"]
46
  return text
47
 
48
- # Function to generate SOAP notes using Llama model
49
- def generate_soap(transcribed_text):
50
- # Format the conversation for the Llama model
51
- prompt = [
52
- {"role": "system", "content": sys_prompt},
53
- {"role": "user", "content": f"{task_prompt}\n{transcribed_text}"}
54
- ]
 
 
 
 
 
 
 
 
 
 
 
 
 
 
55
 
56
- # Generate a response
57
- response = llm.create_chat_completion(messages=prompt, temperature=0.7, max_tokens=2048)
58
- return response["choices"][0]["message"]["content"]
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
59
 
60
- # Gradio Interfaces for different inputs
61
  demo = gr.Blocks(theme=gr.themes.Ocean())
62
 
63
  # Interface for microphone or file transcription
64
  mf_transcribe = gr.Interface(
65
  fn=transcribe,
66
- inputs=[gr.Audio(sources="microphone", type="filepath"), gr.Radio(["transcribe", "translate"], label="Task", value="transcribe")],
 
 
 
67
  outputs="text",
68
  title="Audio Transcribe",
69
  description="Transcribe long-form microphone or audio inputs."
@@ -71,22 +106,36 @@ mf_transcribe = gr.Interface(
71
 
72
  file_transcribe = gr.Interface(
73
  fn=transcribe,
74
- inputs=[gr.Audio(sources="upload", type="filepath", label="Audio file"), gr.Radio(["transcribe", "translate"], label="Task", value="transcribe")],
 
 
 
75
  outputs="text",
76
  title="Audio Transcribe"
77
  )
78
 
79
- # SOAP Note generation interface
80
  soap_note = gr.Interface(
81
  fn=generate_soap,
82
- inputs="text",
 
 
 
 
 
 
 
 
83
  outputs="text",
84
  title="Generate Clinical SOAP Note",
85
- description="Convert transcribed conversation to a clinical SOAP note with structured sections (Subjective, Objective, Assessment, Plan)."
86
  )
87
 
88
- # Tabbed interface with transcription and SOAP note generation
89
  with demo:
90
- gr.TabbedInterface([mf_transcribe, file_transcribe, soap_note], ["Microphone", "Audio file", "SOAP Note"])
 
 
 
91
 
92
  demo.queue().launch(ssr_mode=False)
 
1
  import spaces
2
  import torch
3
  import gradio as gr
4
+ from transformers import pipeline, AutoModelForCausalLM, AutoTokenizer
5
+ from threading import Thread
6
+ from typing import Iterator
7
+ import os
8
 
9
  MODEL_NAME = "openai/whisper-large-v3-turbo"
10
  BATCH_SIZE = 8
11
  FILE_LIMIT_MB = 1000
12
+ MAX_INPUT_TOKEN_LENGTH = int(os.getenv("MAX_INPUT_TOKEN_LENGTH", "4096"))
13
 
14
  device = 0 if torch.cuda.is_available() else "cpu"
15
 
16
+ # Initialize the LLM
17
+ if torch.cuda.is_available():
18
+ llm_model_id = "NousResearch/Meta-Llama-3.1-8B-Instruct"
19
+ llm = AutoModelForCausalLM.from_pretrained(llm_model_id, torch_dtype=torch.float16, device_map="auto")
20
+ tokenizer = AutoTokenizer.from_pretrained(llm_model_id)
21
+ tokenizer.use_default_system_prompt = False
22
 
23
  # Initialize the transcription pipeline
24
  pipe = pipeline(
 
28
  device=device,
29
  )
30
 
 
 
 
 
 
 
 
 
 
 
 
 
 
31
  # Function to transcribe audio inputs
32
  @spaces.GPU
33
  def transcribe(inputs, task):
 
36
  text = pipe(inputs, batch_size=BATCH_SIZE, generate_kwargs={"task": task}, return_timestamps=True)["text"]
37
  return text
38
 
39
+ # Function to generate SOAP notes using LLM
40
+ @spaces.GPU
41
+ def generate_soap(
42
+ transcribed_text: str,
43
+ system_prompt: str = "You are a world class clinical assistant.",
44
+ max_new_tokens: int = 1024,
45
+ temperature: float = 0.6,
46
+ top_p: float = 0.9,
47
+ top_k: int = 50,
48
+ repetition_penalty: float = 1.2,
49
+ ) -> Iterator[str]:
50
+ task_prompt = """
51
+ Convert the following transcribed conversation into a clinical SOAP note.
52
+ The text includes dialogue between a physician and a patient. Please clearly distinguish between the physician's and the patient's statements.
53
+ Extract and organize the information into the relevant sections of a SOAP note:
54
+ - Subjective (symptoms and patient statements),
55
+ - Objective (clinical findings and observations),
56
+ - Assessment (diagnosis or potential diagnoses),
57
+ - Plan (treatment and follow-up).
58
+ Ensure the note is concise, clear, and accurately reflects the conversation.
59
+ """
60
 
61
+ conversation = [
62
+ {"role": "system", "content": system_prompt},
63
+ {"role": "user", "content": f"{task_prompt}\n\nTranscribed conversation:\n{transcribed_text}"}
64
+ ]
65
+
66
+ input_ids = tokenizer.apply_chat_template(conversation, return_tensors="pt")
67
+ if input_ids.shape[1] > MAX_INPUT_TOKEN_LENGTH:
68
+ input_ids = input_ids[:, -MAX_INPUT_TOKEN_LENGTH:]
69
+ gr.Warning(f"Trimmed input from conversation as it was longer than {MAX_INPUT_TOKEN_LENGTH} tokens.")
70
+ input_ids = input_ids.to(llm.device)
71
+
72
+ streamer = TextIteratorStreamer(tokenizer, timeout=10.0, skip_prompt=True, skip_special_tokens=True)
73
+ generate_kwargs = dict(
74
+ {"input_ids": input_ids},
75
+ streamer=streamer,
76
+ max_new_tokens=max_new_tokens,
77
+ do_sample=True,
78
+ top_p=top_p,
79
+ top_k=top_k,
80
+ temperature=temperature,
81
+ num_beams=1,
82
+ repetition_penalty=repetition_penalty,
83
+ )
84
+ t = Thread(target=llm.generate, kwargs=generate_kwargs)
85
+ t.start()
86
+
87
+ outputs = []
88
+ for text in streamer:
89
+ outputs.append(text)
90
+ yield "".join(outputs)
91
 
92
+ # Gradio Interfaces
93
  demo = gr.Blocks(theme=gr.themes.Ocean())
94
 
95
  # Interface for microphone or file transcription
96
  mf_transcribe = gr.Interface(
97
  fn=transcribe,
98
+ inputs=[
99
+ gr.Audio(sources="microphone", type="filepath"),
100
+ gr.Radio(["transcribe", "translate"], label="Task", value="transcribe")
101
+ ],
102
  outputs="text",
103
  title="Audio Transcribe",
104
  description="Transcribe long-form microphone or audio inputs."
 
106
 
107
  file_transcribe = gr.Interface(
108
  fn=transcribe,
109
+ inputs=[
110
+ gr.Audio(sources="upload", type="filepath", label="Audio file"),
111
+ gr.Radio(["transcribe", "translate"], label="Task", value="transcribe")
112
+ ],
113
  outputs="text",
114
  title="Audio Transcribe"
115
  )
116
 
117
+ # SOAP Note generation interface with additional parameters
118
  soap_note = gr.Interface(
119
  fn=generate_soap,
120
+ inputs=[
121
+ gr.Textbox(label="Transcribed Text", lines=10),
122
+ gr.Textbox(label="System Prompt", lines=2, value="You are a world class clinical assistant."),
123
+ gr.Slider(label="Max new tokens", minimum=1, maximum=2048, value=1024, step=1),
124
+ gr.Slider(label="Temperature", minimum=0.1, maximum=4.0, value=0.6, step=0.1),
125
+ gr.Slider(label="Top-p", minimum=0.05, maximum=1.0, value=0.9, step=0.05),
126
+ gr.Slider(label="Top-k", minimum=1, maximum=1000, value=50, step=1),
127
+ gr.Slider(label="Repetition penalty", minimum=1.0, maximum=2.0, value=1.2, step=0.05)
128
+ ],
129
  outputs="text",
130
  title="Generate Clinical SOAP Note",
131
+ description="Convert transcribed conversation to a clinical SOAP note with structured sections."
132
  )
133
 
134
+ # Tabbed interface
135
  with demo:
136
+ gr.TabbedInterface(
137
+ [mf_transcribe, file_transcribe, soap_note],
138
+ ["Microphone", "Audio file", "SOAP Note"]
139
+ )
140
 
141
  demo.queue().launch(ssr_mode=False)