# This program places questions in an existing homework assignment from canvasapi import Canvas from canvasapi import exceptions as canvas_exceptions from os import chdir, listdir import csv from time import sleep # location of the questions API_URL = 'https://asu.instructure.com' API_KEY = '''put api key here''' # Initialize a new Canvas object canvas = Canvas(API_URL, API_KEY) print('type of canvas:',type(canvas)) # test course courseno = '''canvas course number for your courses''' #mat343 course = canvas.get_course(courseno) inventory = [] with open('/Volumes/NO NAME/inventoryQ3_mat343.txt','r') as f : csvreader = csv.reader(f, delimiter='\t') for row in csvreader : inventory += [row] assignment_name = 'quiz3' # get all the assignments from the Canvas course assignments = course.get_assignments() # assignments is a paginated list # run through until you find the one you want for a in assignments: if assignment_name in a.name: assignment = a print('assignment:', assignment) else : print(a) continue '''note that you need to set the assignment submission type to online:file_uploads, and the dates of submission need to include the date that you're actually submitting''' for indx in range(len(inventory)) : row = inventory[ indx ] if row[5][-4:] != '.pdf' : print('row has no filename:',row) continue print(row[0],row[1]) stu_id = row[1] # This is the ID from the Canvas gradebook for the student # The assignment must already exist in Canvas, be sure to create it first # The assignment name is a unique portion of the assignment name in canvas # location of the file to upload file_name = '/Volumes/NO NAME/quiz3/' + row[ 5 ] # Uploading directly to the assignment submission generates an error. # First upload the file and associate with the student try : file_submission_tuple = assignment.upload_to_submission(file_name, user=stu_id) except canvas_exceptions.Forbidden as err : print('forbidden exception#1', row[0], row[1], err) continue # get the dictionary of information about the file that includes the id of the file file_submission = file_submission_tuple[1] #print('file_submission', file_submission) # create a submission for the student submission = {} submission[ 'user_id' ] = stu_id submission[ 'submission_type' ] = 'online_upload' # the file has already been uploaded to canvas # associate the file with this submission here # I believe this "tricks" Canvas into thinking the student uploaded the file submission['file_ids'] = [file_submission['id']] # create a dictionary with the details of the submission try : assignment.submit(submission) except canvas_exceptions.Forbidden as err : print('forbidden exception#2', row[0], err) continue # grading requires updating the subission. Probably because canvas thinks the initial submission comes from the student submission = assignment.get_submission(stu_id) submission.edit(submission={'posted_grade':row[3]}) sleep(1) # // The submission's assignment id # "assignment_id": 23, # // The submission's assignment (see the assignments API) (optional) # "assignment": null, # // The submission's course (see the course API) (optional) # "course": null, # // This is the submission attempt number. # "attempt": 1, # // The content of the submission, if it was submitted directly in a text field. # "body": "There are three factors too...", # // The grade for the submission, translated into the assignment grading scheme # // (so a letter grade, for example). # "grade": "A-", # // A boolean flag which is false if the student has re-submitted since the # // submission was last graded. # "grade_matches_current_submission": true, # // URL to the submission. This will require the user to log in. # "html_url": "http://example.com/courses/255/assignments/543/submissions/134", # // URL to the submission preview. This will require the user to log in. # "preview_url": "http://example.com/courses/255/assignments/543/submissions/134?preview=1", # // The raw score # "score": 13.5, # // Associated comments for a submission (optional) # "submission_comments": null, # // The types of submission ex: # // ('online_text_entry'|'online_url'|'online_upload'|'online_quiz'|'media_record # // ing'|'student_annotation') # "submission_type": "online_text_entry", # // The timestamp when the assignment was submitted # "submitted_at": "2012-01-01T01:00:00Z", # // The URL of the submission (for 'online_url' submissions). # "url": null, # // The id of the user who created the submission # "user_id": 134, # // The id of the user who graded the submission. This will be null for # // submissions that haven't been graded yet. It will be a positive number if a # // real user has graded the submission and a negative number if the submission # // was graded by a process (e.g. Quiz autograder and autograding LTI tools). # // Specifically autograded quizzes set grader_id to the negative of the quiz id. # // Submissions autograded by LTI tools set grader_id to the negative of the tool # // id. # "grader_id": 86, # "graded_at": "2012-01-02T03:05:34Z", # // The submissions user (see user API) (optional) # "user": null, # // Whether the submission was made after the applicable due date # "late": false, # // Whether the assignment is visible to the user who submitted the assignment. # // Submissions where `assignment_visible` is false no longer count towards the # // student's grade and the assignment can no longer be accessed by the student. # // `assignment_visible` becomes false for submissions that do not have a grade # // and whose assignment is no longer assigned to the student's section. # "assignment_visible": true, # // Whether the assignment is excused. Excused assignments have no impact on a # // user's grade. # "excused": true, # // Whether the assignment is missing. # "missing": true, # // The status of the submission in relation to the late policy. Can be late, # // missing, extended, none, or null. # "late_policy_status": "missing", # // The amount of points automatically deducted from the score by the # // missing/late policy for a late or missing assignment. # "points_deducted": 12.3, # // The amount of time, in seconds, that an submission is late by. # "seconds_late": 300, # // The current state of the submission # "workflow_state": "submitted", # // Extra submission attempts allowed for the given user and assignment. # "extra_attempts": 10, # // A unique short ID identifying this submission without reference to the owning # // user. Only included if the caller has administrator access for the current # // account. # "anonymous_id": "acJ4Q", # // The date this submission was posted to the student, or nil if it has not been # // posted. # "posted_at": "2020-01-02T11:10:30Z", # // The read status of this submission for the given user (optional). Including # // read_status will mark submission(s) as read. # "read_status": "read", # // This indicates whether the submission has been reassigned by the instructor. # "redo_request": true # }