sedaklc commited on
Commit
4d117cc
·
verified ·
1 Parent(s): ced3722

Upload app.py with huggingface_hub

Browse files
Files changed (1) hide show
  1. app.py +131 -80
app.py CHANGED
@@ -1,99 +1,150 @@
1
- import torch
2
  import gradio as gr
3
- from transformers import AutoModelForCausalLM, AutoTokenizer, BitsAndBytesConfig
4
- from peft import PeftModel
5
 
6
- MODEL_ID = "codellama/CodeLlama-7b-hf"
7
- ADAPTER_ID = "sedaklc/codellama-7b-qlora-humaneval"
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
8
 
9
- print("Loading model...")
10
- bnb_config = BitsAndBytesConfig(
11
- load_in_4bit=True,
12
- bnb_4bit_quant_type="nf4",
13
- bnb_4bit_use_double_quant=True,
14
- bnb_4bit_compute_dtype=torch.bfloat16,
15
- )
16
 
17
- tokenizer = AutoTokenizer.from_pretrained(ADAPTER_ID)
18
- tokenizer.pad_token = tokenizer.eos_token
19
- tokenizer.padding_side = "right"
20
 
21
- base_model = AutoModelForCausalLM.from_pretrained(
22
- MODEL_ID,
23
- quantization_config=bnb_config,
24
- device_map="auto",
25
- torch_dtype=torch.bfloat16,
26
- )
27
- model = PeftModel.from_pretrained(base_model, ADAPTER_ID)
28
- model.eval()
29
- print("Model ready.")
30
 
31
 
32
- def generate_completion(docstring: str, temperature: float, max_new_tokens: int) -> str:
33
- if not docstring.strip():
34
- return ""
35
- prompt = f"[INST] {docstring.strip()} [/INST]\n"
36
- inputs = tokenizer(prompt, return_tensors="pt", truncation=True, max_length=512).to(model.device)
37
- with torch.no_grad():
38
- output = model.generate(
39
- **inputs,
40
- max_new_tokens=int(max_new_tokens),
41
- temperature=temperature,
42
- top_p=0.95,
43
- do_sample=True,
44
- pad_token_id=tokenizer.eos_token_id,
45
- )
46
- new_tokens = output[0][inputs["input_ids"].shape[1]:]
47
- return tokenizer.decode(new_tokens, skip_special_tokens=True)
48
-
49
-
50
- EXAMPLES = [
51
- ["Return n-th Fibonacci number.", 0.2, 256],
52
- ["Filter an input list of strings only for ones that start with a given prefix.", 0.2, 256],
53
- ["Return True if list elements are monotonically increasing or decreasing.\n>>> monotonic([1, 2, 4, 20])\nTrue\n>>> monotonic([1, 20, 4, 10])\nFalse", 0.2, 256],
54
- ["Return median of elements in the list l.\n>>> median([3, 1, 2, 4, 5])\n3\n>>> median([-10, 4, 6, 1000, 10, 3])\n8.0", 0.2, 256],
55
- ["Return list of prime factors of given integer in the order from smallest to largest.\n>>> factorize(8)\n[2, 2, 2]\n>>> factorize(25)\n[5, 5]", 0.2, 256],
56
- ]
57
-
58
- with gr.Blocks(title="CodeLlama-7B QLoRA — Python Code Completion") as demo:
59
  gr.Markdown(
60
  """
61
  # CodeLlama-7B QLoRA — Python Code Completion
62
 
63
- Fine-tuned on CodeSearchNet Python with LoRA (rank=8) and evaluated on HumanEval.
64
- **Results:** pass@1 = 26.83% · pass@5 = 35.91% · pass@10 = 38.41%
65
- Model: [`sedaklc/codellama-7b-qlora-humaneval`](https://huggingface.co/sedaklc/codellama-7b-qlora-humaneval)
66
- """
67
- )
68
 
69
- with gr.Row():
70
- with gr.Column():
71
- docstring = gr.Textbox(
72
- label="Python function docstring",
73
- placeholder="Describe the function you want implemented...",
74
- lines=6,
75
- )
76
- with gr.Row():
77
- temperature = gr.Slider(
78
- minimum=0.01, maximum=1.0, value=0.2, step=0.01, label="Temperature"
79
- )
80
- max_tokens = gr.Slider(
81
- minimum=64, maximum=512, value=256, step=32, label="Max new tokens"
82
- )
83
- submit_btn = gr.Button("Generate", variant="primary")
84
 
85
- with gr.Column():
86
- output = gr.Textbox(label="Generated code", lines=16)
 
 
87
 
88
- gr.Examples(
89
- examples=EXAMPLES,
90
- inputs=[docstring, temperature, max_tokens],
91
- outputs=output,
92
- fn=generate_completion,
93
- cache_examples=False,
94
  )
95
 
96
- submit_btn.click(fn=generate_completion, inputs=[docstring, temperature, max_tokens], outputs=output)
 
 
 
 
 
 
 
 
 
 
 
 
 
 
97
 
98
  if __name__ == "__main__":
99
  demo.launch()
 
 
1
  import gradio as gr
 
 
2
 
3
+ EXAMPLES = {
4
+ "has_close_elements check threshold proximity": {
5
+ "docstring": (
6
+ "Check if in given list of numbers, are any two numbers closer to each\n"
7
+ "other than given threshold.\n"
8
+ ">>> has_close_elements([1.0, 2.0, 3.0], 0.5)\n"
9
+ "False\n"
10
+ ">>> has_close_elements([1.0, 2.8, 3.0, 4.0, 5.0, 2.0], 0.3)\n"
11
+ "True"
12
+ ),
13
+ "completion": (
14
+ "def has_close_elements(numbers: List[float], threshold: float) -> bool:\n"
15
+ " for i in range(len(numbers)):\n"
16
+ " for j in range(i + 1, len(numbers)):\n"
17
+ " if abs(numbers[i] - numbers[j]) < threshold:\n"
18
+ " return True\n"
19
+ " return False"
20
+ ),
21
+ },
22
+ "separate_paren_groups — split nested parentheses": {
23
+ "docstring": (
24
+ "Input to this function is a string containing multiple groups of nested\n"
25
+ "parentheses. Your goal is to separate those groups into separate strings\n"
26
+ "and return the list of those. Separate groups are balanced (each open\n"
27
+ "brace is properly closed) and not nested within each other. Ignore any\n"
28
+ "spaces in the input string.\n"
29
+ ">>> separate_paren_groups('( ) (( )) (( )( ))')\n"
30
+ "['()', '(())', '(()())']"
31
+ ),
32
+ "completion": (
33
+ "def separate_paren_groups(paren_string: str) -> List[str]:\n"
34
+ " result = []\n"
35
+ " depth = 0\n"
36
+ " current = ''\n"
37
+ " for char in paren_string:\n"
38
+ " if char == '(':\n"
39
+ " depth += 1\n"
40
+ " current += char\n"
41
+ " elif char == ')':\n"
42
+ " depth -= 1\n"
43
+ " current += char\n"
44
+ " if depth == 0:\n"
45
+ " result.append(current)\n"
46
+ " current = ''\n"
47
+ " return result"
48
+ ),
49
+ },
50
+ "rescale_to_unit — linear normalisation to [0, 1]": {
51
+ "docstring": (
52
+ "Given a list of numbers (of at least two elements), apply a linear\n"
53
+ "transform to that list, such that the smallest number will become 0 and\n"
54
+ "the largest will become 1.\n"
55
+ ">>> rescale_to_unit([1.0, 2.0, 3.0, 4.0, 5.0])\n"
56
+ "[0.0, 0.25, 0.5, 0.75, 1.0]"
57
+ ),
58
+ "completion": (
59
+ "def rescale_to_unit(numbers: List[float]) -> List[float]:\n"
60
+ " min_val = min(numbers)\n"
61
+ " max_val = max(numbers)\n"
62
+ " return [(x - min_val) / (max_val - min_val) for x in numbers]"
63
+ ),
64
+ },
65
+ "remove_duplicates — keep only unique elements": {
66
+ "docstring": (
67
+ "From a list of integers, remove all elements that occur more than once.\n"
68
+ "Keep the order of elements left the same as in the input.\n"
69
+ ">>> remove_duplicates([1, 2, 3, 2, 4])\n"
70
+ "[1, 3, 4]"
71
+ ),
72
+ "completion": (
73
+ "def remove_duplicates(numbers: List[int]) -> List[int]:\n"
74
+ " from collections import Counter\n"
75
+ " counts = Counter(numbers)\n"
76
+ " return [x for x in numbers if counts[x] == 1]"
77
+ ),
78
+ },
79
+ "sort_third — sort every third index in-place": {
80
+ "docstring": (
81
+ "This function takes a list l and returns a list l' such that l' is\n"
82
+ "identical to l in the indices that are not divisible by three, while\n"
83
+ "its values at the indices that are divisible by three are equal to the\n"
84
+ "values of the corresponding indices of l, but sorted.\n"
85
+ ">>> sort_third([1, 2, 3])\n"
86
+ "[1, 2, 3]\n"
87
+ ">>> sort_third([5, 6, 3, 4, 8, 9, 2])\n"
88
+ "[2, 6, 3, 4, 8, 9, 5]"
89
+ ),
90
+ "completion": (
91
+ "def sort_third(l: list) -> list:\n"
92
+ " thirds = sorted(l[i] for i in range(0, len(l), 3))\n"
93
+ " result = list(l)\n"
94
+ " j = 0\n"
95
+ " for i in range(0, len(l), 3):\n"
96
+ " result[i] = thirds[j]\n"
97
+ " j += 1\n"
98
+ " return result"
99
+ ),
100
+ },
101
+ }
102
 
103
+ EXAMPLE_NAMES = list(EXAMPLES.keys())
 
 
 
 
 
 
104
 
 
 
 
105
 
106
+ def load_example(name: str):
107
+ ex = EXAMPLES[name]
108
+ return ex["docstring"], ex["completion"]
 
 
 
 
 
 
109
 
110
 
111
+ with gr.Blocks(title="CodeLlama-7B QLoRA Python Code Completion Demo") as demo:
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
112
  gr.Markdown(
113
  """
114
  # CodeLlama-7B QLoRA — Python Code Completion
115
 
116
+ Fine-tuned on CodeSearchNet Python with LoRA (rank=8) · Evaluated on HumanEval
 
 
 
 
117
 
118
+ | pass@1 | pass@5 | pass@10 |
119
+ |--------|--------|---------|
120
+ | 26.83% | 35.91% | 38.41% |
 
 
 
 
 
 
 
 
 
 
 
 
121
 
122
+ > **Pre-computed outputs from fine-tuned CodeLlama-7B + QLoRA model (inference requires GPU)**
123
+ > Model: [`sedaklc/codellama-7b-qlora-humaneval`](https://huggingface.co/sedaklc/codellama-7b-qlora-humaneval)
124
+ """
125
+ )
126
 
127
+ dropdown = gr.Dropdown(
128
+ choices=EXAMPLE_NAMES,
129
+ value=EXAMPLE_NAMES[0],
130
+ label="Select a HumanEval problem",
 
 
131
  )
132
 
133
+ with gr.Row():
134
+ docstring_box = gr.Textbox(
135
+ label="Docstring (input prompt)",
136
+ lines=10,
137
+ interactive=False,
138
+ )
139
+ completion_box = gr.Code(
140
+ label="Model completion (output)",
141
+ language="python",
142
+ lines=10,
143
+ interactive=False,
144
+ )
145
+
146
+ dropdown.change(fn=load_example, inputs=dropdown, outputs=[docstring_box, completion_box])
147
+ demo.load(fn=load_example, inputs=dropdown, outputs=[docstring_box, completion_box])
148
 
149
  if __name__ == "__main__":
150
  demo.launch()