Thang Truong commited on
Commit
aa4cf69
·
1 Parent(s): 04609eb

initial update

Browse files
This view is limited to 50 files because it contains too many changes.   See raw diff
.gitattributes CHANGED
@@ -32,4 +32,9 @@ saved_model/**/* filter=lfs diff=lfs merge=lfs -text
32
  *.xz filter=lfs diff=lfs merge=lfs -text
33
  *.zip filter=lfs diff=lfs merge=lfs -text
34
  *.zst filter=lfs diff=lfs merge=lfs -text
 
 
 
 
 
35
  *tfevents* filter=lfs diff=lfs merge=lfs -text
 
32
  *.xz filter=lfs diff=lfs merge=lfs -text
33
  *.zip filter=lfs diff=lfs merge=lfs -text
34
  *.zst filter=lfs diff=lfs merge=lfs -text
35
+ *.csv filter=lfs diff=lfs merge=lfs -text
36
+ *.db filter=lfs diff=lfs merge=lfs -text
37
+ *.html filter=lfs diff=lfs merge=lfs -text
38
+ *.jpg filter=lfs diff=lfs merge=lfs -text
39
+ *.jpeg filter=lfs diff=lfs merge=lfs -text
40
  *tfevents* filter=lfs diff=lfs merge=lfs -text
README.md CHANGED
@@ -1,9 +1,11 @@
1
  ---
2
- title: Testing Blind
3
- emoji: 👀
4
- colorFrom: blue
5
- colorTo: yellow
6
- sdk: docker
 
 
7
  pinned: false
8
  ---
9
 
 
1
  ---
2
+ title: BlindTest
3
+ emoji: 🏆
4
+ colorFrom: gray
5
+ colorTo: green
6
+ sdk: gradio
7
+ sdk_version: 5.44.1
8
+ app_file: app.py
9
  pinned: false
10
  ---
11
 
__pycache__/app.cpython-312.pyc ADDED
Binary file (11.6 kB). View file
 
app.py ADDED
@@ -0,0 +1,268 @@
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
+ import threading
2
+ from flask import Flask, g, render_template, request, redirect, url_for, session
3
+ import os
4
+ import time
5
+
6
+ from huggingface_hub import login, HfApi, hf_hub_download # For Hugging Face integration
7
+ import os
8
+ import logging
9
+
10
+ import csv
11
+ import random
12
+ import shortuuid
13
+ import json
14
+ import pandas as pd
15
+ from filelock import FileLock
16
+
17
+
18
+ # Flask application setup
19
+ app = Flask(__name__)
20
+ import os, secrets
21
+
22
+ app = Flask(__name__)
23
+
24
+ # Use a persistent env var in prod; fallback only for local/dev
25
+ app.config["SECRET_KEY"] = os.environ.get("FLASK_SECRET_KEY") or secrets.token_hex(32)
26
+
27
+ # app.config['SECRET_KEY'] = os.environ.get('FLASK_SECRET_KEY') # required for sessions
28
+
29
+ app.config.update(
30
+ SESSION_COOKIE_SAMESITE="None", # allow cross-site
31
+ SESSION_COOKIE_SECURE=True # required for "None"
32
+ )
33
+
34
+ logging.basicConfig(
35
+ level=logging.DEBUG, # Set to DEBUG for more granular logs
36
+ format='%(asctime)s - %(levelname)s - %(message)s',
37
+ handlers=[
38
+ logging.StreamHandler()
39
+ ]
40
+ )
41
+ logger = logging.getLogger(__name__)
42
+
43
+
44
+ HF_TOKEN = os.environ.get("HF_TOKEN")
45
+ if HF_TOKEN:
46
+ try:
47
+ login(token=HF_TOKEN)
48
+ logger.info("Logged into Hugging Face successfully.")
49
+ except Exception as e:
50
+ logger.exception(f"Failed to log into Hugging Face: {e}")
51
+ else:
52
+ logger.warning("HF_TOKEN not found in environment variables. Session data will not be uploaded.")
53
+
54
+ # Initialize Hugging Face API
55
+ hf_api = HfApi()
56
+
57
+
58
+ HF_REPO_ID = "pooyanrg/BlindTest" # Update as needed
59
+ HF_REPO_PATH = "responses"
60
+
61
+
62
+ QUESTIONS_FILE = "./data/dataset.csv"
63
+ AVAILABLE_FILE = "/tmp/available.json"
64
+ LOCK_FILE = "/tmp/available.lock"
65
+
66
+ # Load questions into memory
67
+ with open(QUESTIONS_FILE, newline="", encoding="utf-8") as f:
68
+ reader = csv.DictReader(f)
69
+ all_questions = list(reader)
70
+
71
+ # Track which questions are available
72
+ if not os.path.exists(AVAILABLE_FILE):
73
+ with open(AVAILABLE_FILE, "w") as f:
74
+ json.dump(list(range(len(all_questions))), f)
75
+
76
+ def get_questions(num=10):
77
+ with FileLock(LOCK_FILE):
78
+ with open(AVAILABLE_FILE, "r") as f:
79
+ available = json.load(f)
80
+
81
+ if len(available) == 0:
82
+ return [] # Not enough questions left
83
+
84
+ sample_size = num if num < len(available) else len(available)
85
+ selected_ids = random.sample(available, sample_size)
86
+
87
+ remaining = [qid for qid in available if qid not in selected_ids]
88
+
89
+ with open(AVAILABLE_FILE, "w") as f:
90
+ json.dump(remaining, f)
91
+
92
+ return [all_questions[qid] | {"id": qid} for qid in selected_ids]
93
+
94
+
95
+ @app.route("/", methods=['GET', 'POST'])
96
+ def splash():
97
+ if request.method == 'POST':
98
+ username = request.form.get('username')
99
+
100
+ if not username:
101
+ logger.warning("Username not provided by the user.")
102
+ return render_template('splash.html', error="Please enter a username.")
103
+
104
+ return redirect(url_for('instructions', username=username))
105
+
106
+ # GET request - show intro page
107
+ logger.info("Splash page rendered.")
108
+ return render_template('splash.html')
109
+
110
+
111
+ @app.route('/instructions', methods=['GET', 'POST'])
112
+ def instructions():
113
+ username = request.args.get('username')
114
+ questions = get_questions(num=2)
115
+ current_index = 0
116
+ answers = []
117
+ session['questions'] = questions
118
+ session['answers'] = answers
119
+ q_ids = [question['image_id'] for question in questions]
120
+
121
+ if len(questions) == 0:
122
+ return render_template('thanks.html')
123
+
124
+ if request.method == 'POST':
125
+ # User clicked the "Begin Quiz" button
126
+ start_time = time.time()
127
+ session['start_time'] = start_time
128
+ session['question_ids'] = q_ids
129
+ return redirect(url_for('prep', username=username, current_index=current_index))
130
+
131
+ # If GET, render the final instructions page
132
+ return render_template('instructions.html', username=username)
133
+
134
+
135
+
136
+ @app.route('/prep', methods=['GET', 'POST'])
137
+ def prep():
138
+ username = request.args.get('username')
139
+ current_index = int(request.args.get('current_index'))
140
+
141
+ questions = session.get('questions', [])
142
+
143
+
144
+ if request.method == 'POST':
145
+ # User clicked "Start" button
146
+ # Redirect to the actual question display
147
+ return redirect(url_for('prompt', username=username, current_index=current_index))
148
+
149
+ return render_template('prep.html',
150
+ question_number=current_index + 1,
151
+ total=len(questions))
152
+
153
+ @app.route('/prompt', methods=['GET', 'POST'])
154
+ def prompt():
155
+ username = request.args.get('username')
156
+ current_index = int(request.args.get('current_index'))
157
+
158
+ questions = session.get('questions', [])
159
+
160
+ if request.method == 'POST':
161
+ # User clicked "Start" button
162
+ # Redirect to the image display
163
+ return redirect(url_for('image', username=username, current_index=current_index))
164
+
165
+ question_raw = questions[current_index].get('question', '')
166
+ if "count" in question_raw.lower():
167
+ idx = question_raw.index('.')
168
+ else:
169
+ idx = question_raw.index('?')
170
+
171
+ question = question_raw[:idx+1]
172
+
173
+ task = questions[current_index].get('task', '')
174
+ if task == 'Counting Grid - Blank Grids' or task == 'Counting Grid - Word Grids':
175
+ question = "Count the number of rows and columns."
176
+
177
+ return render_template('prompt.html',
178
+ question_text=question)
179
+
180
+ @app.route('/image', methods=['GET', 'POST'])
181
+ def image():
182
+ username = request.args.get('username')
183
+ current_index = int(request.args.get('current_index'))
184
+
185
+ questions = session.get('questions', [])
186
+ image_id = str(questions[current_index].get('image_id', 'default_image.png'))
187
+
188
+ if request.method == 'POST':
189
+ # Move on to the "quiz" route to see if we still have more questions
190
+ return redirect(url_for('respond', username=username, current_index=current_index))
191
+
192
+ # If GET, display the current image with a 10-seconds countdown
193
+ return render_template('image.html',
194
+ image_name=image_id + '.jpg')
195
+
196
+
197
+ @app.route('/respond', methods=['GET', 'POST'])
198
+ def respond():
199
+ username = request.args.get('username')
200
+ current_index = int(request.args.get('current_index'))
201
+ questions = session.get('questions', [])
202
+ answers = session.get('answers', [])
203
+
204
+ if request.method == 'POST':
205
+ response = request.form.get('response')
206
+ question_id = questions[current_index]['image_id']
207
+
208
+ # Submit the answer
209
+ answers.append({"image_id": question_id,
210
+ "answer": response})
211
+
212
+ session['answers'] = answers
213
+ current_index += 1
214
+
215
+ if current_index >= len(questions):
216
+ # Store the elapsed time
217
+ start_time = session.get('start_time', time.time())
218
+ q_ids = session.get('question_ids', [])
219
+ end_time = time.time()
220
+ elapsed_time = end_time - start_time
221
+
222
+ response_all = {'username': username,
223
+ 'time': elapsed_time,
224
+ 'responses':answers}
225
+
226
+ json_data = json.dumps(response_all, indent=4)
227
+
228
+ file_name = f"{shortuuid.uuid()}.json"
229
+ temp_file_path = os.path.join("/tmp", file_name)
230
+
231
+ with open(temp_file_path, 'w') as f:
232
+ f.write(json_data)
233
+
234
+ return render_template('thanks.html')
235
+
236
+ return redirect(url_for('prep', username=username, current_index=current_index))
237
+
238
+ question_raw = questions[current_index].get('question', '')
239
+ if "count" in question_raw.lower():
240
+ idx = question_raw.index('.')
241
+ else:
242
+ idx = question_raw.index('?')
243
+
244
+ question = question_raw[:idx+1]
245
+
246
+ task = questions[current_index].get('task', '')
247
+ if task == 'Circled Letter':
248
+ form = "Enter a letter"
249
+ elif task == 'Touching Circles':
250
+ form = "Enter Y/N"
251
+ elif task == 'Counting Grid - Blank Grids' or task == 'Counting Grid - Word Grids':
252
+ form = "Enter two numbers seperated with a comma, for example: 5,6"
253
+ question = "Count the number of rows and columns."
254
+ else:
255
+ form = "Enter a number"
256
+
257
+ return render_template('respond.html',
258
+ question_text=question,
259
+ instruction=form)
260
+
261
+
262
+ if __name__ == "__main__":
263
+ # Initialize database when running the script
264
+ # example_usage()
265
+
266
+ # Run Flask app
267
+ # app.run(debug=False, threaded=True)
268
+ app.run(host="0.0.0.0", port=7860, debug=False)
data/dataset.csv ADDED
@@ -0,0 +1,3 @@
 
 
 
 
1
+ version https://git-lfs.github.com/spec/v1
2
+ oid sha256:22783cc71fe58520285ed74afa62e427f79841a6917ff100884f654231ca5466
3
+ size 82879
requirements.txt ADDED
@@ -0,0 +1,6 @@
 
 
 
 
 
 
 
1
+ huggingface_hub
2
+ Flask==2.3.2
3
+ Flask-Session==0.5.0
4
+ pandas==1.5.3
5
+ numpy==1.23.5
6
+ shortuuid
static/.DS_Store ADDED
Binary file (8.2 kB). View file
 
static/images/.DS_Store ADDED
Binary file (6.15 kB). View file
 
static/images/1.jpg ADDED

Git LFS Details

  • SHA256: d39f746bf970f7dc59a7841cd710959fb1db5f7ba59df0ef1a6e5e33969f73e9
  • Pointer size: 130 Bytes
  • Size of remote file: 46.8 kB
static/images/10.jpg ADDED

Git LFS Details

  • SHA256: 13997512d76c843d2755f2475a9712383cd5476c53f85a7c02effc2740f464f5
  • Pointer size: 130 Bytes
  • Size of remote file: 45.7 kB
static/images/100.jpg ADDED

Git LFS Details

  • SHA256: f4ccb5b95ddcc394aae2a2b91fb6651d0c9aca3dc11e3c30854f7520a12a96c0
  • Pointer size: 131 Bytes
  • Size of remote file: 125 kB
static/images/101.jpg ADDED

Git LFS Details

  • SHA256: 18fb044c54e0beda0c39099ade0495eb5e189eb39a378acf98d5c219230cf2af
  • Pointer size: 131 Bytes
  • Size of remote file: 135 kB
static/images/102.jpg ADDED

Git LFS Details

  • SHA256: cc7de1d94a43ecc6d8d0dcc5a5902b467a0dd97c4ed88435c7c11892fd38f283
  • Pointer size: 131 Bytes
  • Size of remote file: 137 kB
static/images/103.jpg ADDED

Git LFS Details

  • SHA256: 639eaa4167cce687a9c7df231f152261805b9af30e71f22355cb608c5eede3b1
  • Pointer size: 131 Bytes
  • Size of remote file: 130 kB
static/images/104.jpg ADDED

Git LFS Details

  • SHA256: fdcecac1113959e443b909bdf6a5b243a9ce11ce6fadcb8e6f036e33b3a43001
  • Pointer size: 130 Bytes
  • Size of remote file: 97.6 kB
static/images/105.jpg ADDED

Git LFS Details

  • SHA256: 947f9b197cbadd81b06977e6a073f690fdb2549d57a5e8640c762f96a3f5445f
  • Pointer size: 130 Bytes
  • Size of remote file: 90.4 kB
static/images/106.jpg ADDED

Git LFS Details

  • SHA256: 5437069476f742f70441f5085b564054ebc07e1932df9e806a3e26a00f1bc74f
  • Pointer size: 131 Bytes
  • Size of remote file: 108 kB
static/images/107.jpg ADDED

Git LFS Details

  • SHA256: 42098ed4f953e25441de004fea1af9eb1c15ebef308e04d76c0ce8426d6e5f2f
  • Pointer size: 131 Bytes
  • Size of remote file: 114 kB
static/images/108.jpg ADDED

Git LFS Details

  • SHA256: 1488fe900728b503a86e5ebc50e104b4390b11403c4c493da07e8d4c1253214b
  • Pointer size: 131 Bytes
  • Size of remote file: 102 kB
static/images/109.jpg ADDED

Git LFS Details

  • SHA256: 2c819bde226f9f683f236183e57ec3fbaa1be45fb9abdf7ef0c04afb7d7864ca
  • Pointer size: 130 Bytes
  • Size of remote file: 87.8 kB
static/images/11.jpg ADDED

Git LFS Details

  • SHA256: 3b2c7b57edf1a98cc0e7c5f242f5b7cd7ab57f7bb5767276d282145f08b933a9
  • Pointer size: 130 Bytes
  • Size of remote file: 46.6 kB
static/images/110.jpg ADDED

Git LFS Details

  • SHA256: 9864545b7e5653c32d7bf6fc2cfe4ebf87aad6ae278ff22f7b14d84e6ee3bafe
  • Pointer size: 131 Bytes
  • Size of remote file: 106 kB
static/images/111.jpg ADDED

Git LFS Details

  • SHA256: 4dc13f8df664a787f5ccde18afc0d3b41babe2b62924241419711d56f65e099b
  • Pointer size: 131 Bytes
  • Size of remote file: 139 kB
static/images/112.jpg ADDED

Git LFS Details

  • SHA256: 4e76b89ea178f48fcf50ae246fb160dafddb0d9f8e3ed9f5bdf80300fcddc7b3
  • Pointer size: 131 Bytes
  • Size of remote file: 121 kB
static/images/113.jpg ADDED

Git LFS Details

  • SHA256: 83de9cb0eee91a92c23e87a3a2e34bab566998536b4d9483cb2db31300566b42
  • Pointer size: 131 Bytes
  • Size of remote file: 125 kB
static/images/114.jpg ADDED

Git LFS Details

  • SHA256: 207309f3128f15763d79fc80c8aadbf592780289d28fb63dbe300942047e3a04
  • Pointer size: 130 Bytes
  • Size of remote file: 84.4 kB
static/images/115.jpg ADDED

Git LFS Details

  • SHA256: 1a14b4aef8aedb982e9a82e54ab1af127392be818523887f6b17fdf6577f3515
  • Pointer size: 131 Bytes
  • Size of remote file: 138 kB
static/images/116.jpg ADDED

Git LFS Details

  • SHA256: a8ea249d670b980fb0ce19dc69302efe9a676a14fb43337ac17de96910915c95
  • Pointer size: 131 Bytes
  • Size of remote file: 111 kB
static/images/117.jpg ADDED

Git LFS Details

  • SHA256: 02790382c34b68f5e52946b95b70ca839bb88346c5376584be6f7fec33513920
  • Pointer size: 130 Bytes
  • Size of remote file: 81.4 kB
static/images/118.jpg ADDED

Git LFS Details

  • SHA256: baa20f966a7cccefc9b76058ce63cdf6ed1f9b3cdc70d8a25e3f25280f6a6ab8
  • Pointer size: 131 Bytes
  • Size of remote file: 110 kB
static/images/119.jpg ADDED

Git LFS Details

  • SHA256: dd388bf87950c4bb72bcb2ba30cb57f86a30a1c20bc997c202a5702336c470a2
  • Pointer size: 131 Bytes
  • Size of remote file: 143 kB
static/images/12.jpg ADDED

Git LFS Details

  • SHA256: b4e4e0e4d2e68c3e90c970d7a2757250584de1dad79482322b394e91626b9315
  • Pointer size: 130 Bytes
  • Size of remote file: 45.5 kB
static/images/120.jpg ADDED

Git LFS Details

  • SHA256: a4a3765d9dc09a1c74f768b7ec1a59cbd735a9a2ad8cba420958d3d50e846a9f
  • Pointer size: 131 Bytes
  • Size of remote file: 108 kB
static/images/121.jpg ADDED

Git LFS Details

  • SHA256: 60193f04a3ffe8a29c797aa32f0721ec2d744f9a1a8383dcc38b93da99a7e3b4
  • Pointer size: 131 Bytes
  • Size of remote file: 136 kB
static/images/122.jpg ADDED

Git LFS Details

  • SHA256: 49e31848a72f90e9059122bcc1b12a9938d61ac6ba2bc523c996aa9f9682798c
  • Pointer size: 131 Bytes
  • Size of remote file: 113 kB
static/images/123.jpg ADDED

Git LFS Details

  • SHA256: f4897c4a360edecd011b26fd2f6f2b48957367ba166d39d49793b02dd5588c65
  • Pointer size: 131 Bytes
  • Size of remote file: 110 kB
static/images/124.jpg ADDED

Git LFS Details

  • SHA256: af9233f385eff79c1b7877d53502294e2a1bbf7fe8d36efe3ef1b41ec750a1ba
  • Pointer size: 130 Bytes
  • Size of remote file: 91.3 kB
static/images/125.jpg ADDED

Git LFS Details

  • SHA256: ddea72006e297adcb3d60891a76fd5687359d8bc1042d7e94e334eff2d598188
  • Pointer size: 131 Bytes
  • Size of remote file: 151 kB
static/images/126.jpg ADDED

Git LFS Details

  • SHA256: e2aad3aaec0f024e7a41109472c5b9a36d0ca75376a0340a4404f5bcb0f6fb72
  • Pointer size: 131 Bytes
  • Size of remote file: 103 kB
static/images/127.jpg ADDED

Git LFS Details

  • SHA256: 5ffeeca751929ffa128391ecc52d6b2490e358bea376e70aa1df102b8e0b58b9
  • Pointer size: 131 Bytes
  • Size of remote file: 117 kB
static/images/128.jpg ADDED

Git LFS Details

  • SHA256: ac2cc54d5b120fe0f6cb163de672739193129436410269c74f41f49e32d3d2b1
  • Pointer size: 131 Bytes
  • Size of remote file: 126 kB
static/images/129.jpg ADDED

Git LFS Details

  • SHA256: 83cf8ff35c9b7089d46f2f8805cd28bbc8ee19f8d931eb2b4ca0d2cbe4e78ffa
  • Pointer size: 131 Bytes
  • Size of remote file: 126 kB
static/images/13.jpg ADDED

Git LFS Details

  • SHA256: 7efeaf1e350ee4474b04dce9eda0190d1671faac8cbd936cb2186a915960b489
  • Pointer size: 130 Bytes
  • Size of remote file: 46.5 kB
static/images/130.jpg ADDED

Git LFS Details

  • SHA256: abd49c16ffaeb363959f07f615e4a8aa8cb7d9b7a852ff5bce44833661001d21
  • Pointer size: 131 Bytes
  • Size of remote file: 113 kB
static/images/131.jpg ADDED

Git LFS Details

  • SHA256: f02fed65a8c7fbbc78b468ae9618607116305171024de27e6ab5a35730850658
  • Pointer size: 130 Bytes
  • Size of remote file: 93 kB
static/images/132.jpg ADDED

Git LFS Details

  • SHA256: 0920e70bdd2e102f9896d56164bf189191528b0412c78d0327499bc1a5e8eaa3
  • Pointer size: 130 Bytes
  • Size of remote file: 99 kB
static/images/133.jpg ADDED

Git LFS Details

  • SHA256: 9eb17b114062146d856a04eb71a6a8776ddb0e019be48031da1e19dce8b40af5
  • Pointer size: 131 Bytes
  • Size of remote file: 121 kB
static/images/134.jpg ADDED

Git LFS Details

  • SHA256: 7906d43abbe158061a9d8004fcc23db8763244683cd6d58ebde1d1e7ec6915bd
  • Pointer size: 131 Bytes
  • Size of remote file: 111 kB
static/images/135.jpg ADDED

Git LFS Details

  • SHA256: 69fbf7ab1f710ea2a7bd1adedf578623583b1aa97582e58cfad35e73fc41a913
  • Pointer size: 131 Bytes
  • Size of remote file: 167 kB
static/images/136.jpg ADDED

Git LFS Details

  • SHA256: 04f6b099065da3618ade509c09005284cb1011f3ac6c24ca5f4f45f14ab24882
  • Pointer size: 131 Bytes
  • Size of remote file: 108 kB