1. Go to this page and download the library: Download jjuanrivvera/canvas-lms-kit library. Choose the download type require.
2. Extract the ZIP file and open the index.php.
3. Add this code to the index.php.
<?php
require_once('vendor/autoload.php');
/* Start to develop here. Best regards https://php-download.com/ */
jjuanrivvera / canvas-lms-kit example snippets
use CanvasLMS\Config;
use CanvasLMS\Api\Courses\Course;
Config::setApiKey('your-api-key');
Config::setBaseUrl('https://canvas.instructure.com');
// It's that simple!
$courses = Course::get(); // Get first page
foreach ($courses as $course) {
echo $course->name . "\n";
}
use CanvasLMS\Config;
// Basic configuration
Config::setApiKey('your-api-key');
Config::setBaseUrl('https://canvas.instructure.com');
// Optional: Set account ID for scoped operations
Config::setAccountId(1);
// Optional: Configure middleware
Config::setMiddleware([
'retry' => ['max_attempts' => 3],
'rate_limit' => ['wait_on_limit' => true],
]);
use CanvasLMS\Config;
use CanvasLMS\Auth\OAuth;
// Configure OAuth credentials
Config::setOAuthClientId('your-client-id');
Config::setOAuthClientSecret('your-client-secret');
Config::setOAuthRedirectUri('https://yourapp.com/oauth/callback');
Config::setBaseUrl('https://canvas.instructure.com');
// Step 1: Get authorization URL
$authUrl = OAuth::getAuthorizationUrl(['state' => 'random-state']);
// Redirect user to $authUrl
// Step 2: Handle callback
$tokenData = OAuth::exchangeCode($_GET['code']);
// Step 3: Use OAuth mode
Config::useOAuth();
// Now all API calls use OAuth with automatic token refresh!
$courses = Course::get(); // User's courses (first page)
// Auto-detect from environment
Config::autoDetect();
// Ready to use!
use CanvasLMS\Config;
use Monolog\Logger;
use Monolog\Handler\StreamHandler;
// Configure with Monolog
$logger = new Logger('canvas-lms');
$logger->pushHandler(new StreamHandler('logs/canvas.log', Logger::INFO));
Config::setLogger($logger);
// All API calls, OAuth operations, pagination, and file uploads are now logged!
use Psr\Log\LoggerInterface;
public function __construct(LoggerInterface $logger) {
Config::setLogger($logger);
}
use CanvasLMS\Config;
use CanvasLMS\Api\Courses\Course;
use CanvasLMS\Api\Users\User;
// Enable masquerading as user 12345
Config::asUser(12345);
// All API calls will now ->enrollments(); // Also as user 12345
// Stop masquerading
Config::stopMasquerading();
// Subsequent calls are performed as the authenticated user
$normalCourse = Course::find(789); // No masquerading
// Set masquerading for production context only
Config::setContext('production');
Config::asUser(12345, 'production');
// Only affects production context operations
Config::setContext('staging');
$stagingUser = User::find(1); // Not masqueraded
Config::setContext('production');
$prodUser = User::find(1); // Masqueraded as user 12345
// Check if masquerading is active
if (Config::isMasquerading()) {
$masqueradeUserId = Config::getMasqueradeUserId();
$logger->info("Performing operation as user {$masqueradeUserId}");
}
// Support agent helping a student
Config::asUser($studentId);
$submissions = Assignment::find($assignmentId)->getSubmission($studentId);
Config::stopMasquerading();
// Test different user roles
foreach ($testUsers as $userId => $role) {
Config::asUser($userId);
$canEdit = Course::find($courseId)->canEdit(); // Check permissions as this user
echo "User {$userId} ({$role}): " . ($canEdit ? 'Can edit' : 'Cannot edit') . "\n";
}
Config::stopMasquerading();
// Process enrollments for multiple users
$userIds = [123, 456, 789];
foreach ($userIds as $userId) {
Config::asUser($userId);
$enrollment = Enrollment::create([
'user_id' => $userId,
'course_id' => $courseId,
'enrollment_state' => 'active'
]);
echo "Enrolled user {$userId} successfully\n";
}
Config::stopMasquerading();
// 1. get() - Fetch first page only (default: 10 items)
$courses = Course::get(); // First 10 courses
$courses = Course::get(['per_page' => 50]); // First 50 courses
// 2. paginate() - Get results with pagination metadata
$result = Course::paginate(['per_page' => 25]);
echo "Page {$result->getCurrentPage()} of {$result->getTotalPages()}";
echo "Total courses: {$result->getTotalCount()}";
// 3. all() - Fetch ALL items from all pages automatically
$allCourses = Course::all(); // ⚠️ Use with caution on large datasets!
// ❌ WRONG - May exhaust memory with large datasets
$allUsers = User::all(); // Could be 50,000+ users!
foreach ($allUsers as $user) {
processUser($user);
}
// ✅ CORRECT - Process in batches using paginate()
$page = 1;
do {
$batch = User::paginate(['page' => $page++, 'per_page' => 100]);
foreach ($batch->getData() as $user) {
processUser($user);
}
// Optional: Add delay to respect rate limits
if ($batch->hasNextPage()) {
sleep(1);
}
} while ($batch->hasNextPage());
// In your controller
$page = $_GET['page'] ?? 1;
$result = Course::paginate(['page' => $page, 'per_page' => 25]);
// In your view
foreach ($result->getData() as $course) {
echo "<tr><td>{$course->name}</td></tr>";
}
// Pagination controls
if ($result->hasPreviousPage()) {
echo "<a href='?page=" . ($page - 1) . "'>Previous</a>";
}
if ($result->hasNextPage()) {
echo "<a href='?page=" . ($page + 1) . "'>Next</a>";
}
echo "Page {$result->getCurrentPage()} of {$result->getTotalPages()}";
// For small datasets (< 1000 items)
$assignments = Assignment::all(['course_id' => 123]);
exportToCSV($assignments);
// For large datasets - stream to file
$csvFile = fopen('enrollments.csv', 'w');
$page = 1;
do {
$batch = Enrollment::paginate(['page' => $page++, 'per_page' => 500]);
foreach ($batch->getData() as $enrollment) {
fputcsv($csvFile, [
$enrollment->userId,
$enrollment->courseId,
$enrollment->enrollmentState
]);
}
} while ($batch->hasNextPage());
fclose($csvFile);
// When you need just a subset
$recentAssignments = Assignment::get([
'per_page' => 10,
'order_by' => 'due_at'
]);
// When searching through all pages
$found = false;
$page = 1;
do {
$batch = User::paginate([
'page' => $page++,
'search_term' => '[email protected]'
]);
foreach ($batch->getData() as $user) {
if ($user->email === '[email protected]') {
$found = $user;
break 2; // Exit both loops
}
}
} while ($batch->hasNextPage() && !$found);
$result = Course::paginate(['per_page' => 20]);
// Data access
$courses = $result->getData(); // Array of Course objects
$total = $result->getTotalCount(); // Total number of courses
// Navigation
$result->hasNextPage(); // true/false
$result->hasPreviousPage(); // true/false
$result->getNextPage(); // Fetches next page (returns new PaginationResult)
$result->getPreviousPage(); // Fetches previous page
// Page information
$result->getCurrentPage(); // Current page number
$result->getTotalPages(); // Total number of pages
$result->getPerPage(); // Items per page
// URL access (for custom implementations)
$result->getNextUrl(); // Next page URL
$result->getPreviousUrl(); // Previous page URL
// 📗 Small datasets (< 100 items): Safe to use all()
$modules = Module::all();
$sections = Section::all();
// 📙 Medium datasets (100-1000 items): Consider your use case
$assignments = Assignment::get(['per_page' => 100]); // If you need subset
$assignments = Assignment::paginate(['per_page' => 100]); // If processing batches
$assignments = Assignment::all(); // If you need everything
// 📕 Large datasets (1000+ items): Use paginate() for memory efficiency
$users = User::paginate(['per_page' => 100]);
$enrollments = Enrollment::paginate(['per_page' => 500]);
// Note: The SDK
$course = Course::find(123);
$modules = $course->modules(); // Returns ALL modules (all pages)
$enrollments = $course->enrollments(); // Returns ALL enrollments (could be thousands!)
// For large datasets, consider using pagination directly:
Enrollment::setCourse($course);
$paginatedEnrollments = Enrollment::paginate(['per_page' => 100]); // Memory efficient
// Or use paginate for control:
$paginatedModules = Module::paginate(['per_page' => 50]);
use CanvasLMS\Api\Courses\Course;
// Get first page of courses (memory efficient)
$courses = Course::get();
// Get ALL courses across all pages automatically
// ⚠️ Warning: Be cautious with large datasets (1000+ items)
$allCourses = Course::all();
// Get paginated results with metadata (recommended for large datasets)
$paginated = Course::paginate(['per_page' => 50]);
echo "Total courses: " . $paginated->getTotalCount();
// Find a specific course
$course = Course::find(123);
// Create a new course - just pass an array!
$course = Course::create([
'name' => 'Introduction to PHP',
'course_code' => 'PHP101',
'start_at' => '2025-02-01T00:00:00Z'
]);
// Update a course
$course->update([
'name' => 'Advanced PHP Programming'
]);
// Save changes with fluent interface support
$course->name = 'Updated Course Name';
$course->save()->enrollments(); // Save and immediately get enrollments
// Delete a course (also returns self for chaining)
$course->delete();
use CanvasLMS\Api\Assignments\Assignment;
use CanvasLMS\Api\Submissions\Submission;
use CanvasLMS\Api\Courses\Course;
// Set course context for Assignment
$course = Course::find(123);
Assignment::setCourse($course);
// Create an assignment - simple array syntax
$assignment = Assignment::create([
'name' => 'Final Project',
'description' => 'Build a web application',
'points_possible' => 100,
'due_at' => '2025-03-15T23:59:59Z',
'submission_types' => ['online_upload', 'online_url']
]);
// Grade submissions (
use CanvasLMS\Api\Modules\Module;
use CanvasLMS\Api\Modules\ModuleItem;
// Get course and set context
$course = Course::find(123);
Module::setCourse($course);
// Create a module
$module = Module::create([
'name' => 'Week 1: Introduction',
'position' => 1,
'published' => true
]);
// Add items to the module (
]);
// Or use the course instance method (recommended)
$modules = $course->modules();
use CanvasLMS\Api\Users\User;
// Get current authenticated user instance
$currentUser = User::self();
// Canvas supports 'self' for these endpoints:
$profile = $currentUser->getProfile();
$activityStream = $currentUser->getActivityStream();
$todos = $currentUser->getTodoItems();
$groups = $currentUser->groups();
// Other methods
use CanvasLMS\Api\Groups\Group;
use CanvasLMS\Api\Groups\GroupMembership;
// Create a group in your account
$group = Group::create([
'name' => 'Study Group Alpha',
'description' => 'Weekly study sessions',
'is_public' => false,
'join_level' => 'invitation_only'
]);
// Add members to the group
$membership = $group->createMembership([
'user_id' => 456,
'workflow_state' => 'accepted'
]);
// Get group activity stream
$activities = $group->activityStream();
// Invite users by email
$group->invite(['[email protected]', '[email protected]']);
use CanvasLMS\Api\Files\File;
// Upload a file to a course
$file = File::upload([
'course_id' => 123,
'file_path' => '/path/to/document.pdf',
'name' => 'Course Syllabus.pdf',
'parent_folder_path' => 'course_documents'
]);
use CanvasLMS\Api\FeatureFlags\FeatureFlag;
use CanvasLMS\Api\Courses\Course;
// Get feature flags for the account
$flags = FeatureFlag::get(); // First page
$allFlags = FeatureFlag::all(); // All flags
// Get a specific feature flag
$flag = FeatureFlag::find('new_gradebook');
// Enable a feature for the account
$flag->enable();
// Disable a feature
$flag->disable();
// Feature flags for a specific course
$course = Course::find(123);
$courseFlags = $course->featureFlags();
// Enable a feature for a specific course
$courseFlag = $course->getFeatureFlag('anonymous_marking');
$courseFlag->enable();
use CanvasLMS\Api\Conversations\Conversation;
// Get conversations for the current user
$conversations = Conversation::get(['scope' => 'unread']); // First page
$allConversations = Conversation::all(['scope' => 'unread']); // All pages
// Create a new conversation
$conversation = Conversation::create([
'recipients' => ['user_123', 'course_456_students'],
'subject' => 'Assignment Feedback',
'body' => 'Great work on your recent submission!',
'group_conversation' => true
]);
// Add a message to existing conversation
$conversation->addMessage([
'body' => 'Following up on my previous message...',
'attachment_ids' => [789] // Attach files
]);
// Manage conversation state
$conversation->markAsRead();
$conversation->star();
$conversation->archive();
// Batch operations
Conversation::batchUpdate([1, 2, 3], ['event' => 'mark_as_read']);
Conversation::markAllAsRead();
// Get unread count
$unreadCount = Conversation::getUnreadCount();
use CanvasLMS\Api\Rubrics\Rubric;
use CanvasLMS\Api\ExternalTools\ExternalTool;
use CanvasLMS\Api\CalendarEvents\CalendarEvent;
use CanvasLMS\Api\Files\File;
// Direct calls default to Account context
$rubrics = Rubric::get(); // Account-level rubrics (first page)
$tools = ExternalTool::get(); // Account-level external tools (first page)
$events = CalendarEvent::get(); // Account-level calendar events (first page)
$files = File::get(); // Exception: User files (no account context)
// Course-specific access through Course instance
$course = Course::find(123);
$courseRubrics = $course->rubrics(); // Course-specific rubrics
$courseTools = $course->externalTools(); // Course-specific tools
$courseEvents = $course->calendarEvents(); // Course-specific events
$courseFiles = $course->files(); // Course-specific files
// Direct context access when needed
$userEvents = CalendarEvent::fetchByContext('user', 456);
$groupFiles = File::fetchByContext('groups', 789);
// ✅ GOOD: Memory-efficient for large datasets
$result = User::paginate(['per_page' => 100]);
while ($result) {
foreach ($result->getData() as $user) {
// Process batch of 100 users
}
$result = $result->hasNextPage() ? $result->getNextPage() : null;
}
// ✅ GOOD: Get only what you need
$recentCourses = Course::get(['per_page' => 20]); // Just first 20
// ⚠️ CAUTION: Loads entire dataset into memory
$allUsers = User::all(); // Could be 50,000+ users!
$allEnrollments = Enrollment::all(); // Could be millions!
// ⚠️ BETTER: Process in batches for large datasets
$page = 1;
do {
$batch = Enrollment::paginate(['page' => $page++, 'per_page' => 500]);
// Process batch
} while ($batch->hasNextPage());
use CanvasLMS\Api\Pages\Page;
use CanvasLMS\Api\Quizzes\Quiz;
use CanvasLMS\Api\Modules\Module;
use CanvasLMS\Api\DiscussionTopics\DiscussionTopic;
use CanvasLMS\Api\Courses\Course;
// Get your course
$course = Course::find(123);
// Option 1: Set context for each API (:get(); // Get first page
$discussions = DiscussionTopic::all(); // Get all discussions
// Option 2: Use course instance methods (recommended - no context setup needed)
$pages = $course->pages(); // Returns first page only
$quizzes = $course->quizzes(); // Returns first page only
$modules = $course->modules(); // Returns first page only
$discussions = $course->discussionTopics(); // Returns first page only
// Get ALL modules for a course
Module::setCourse($course);
$allModules = Module::all(); // Gets all pages
// Or paginate for control
$paginated = Module::paginate(['per_page' => 50]);
use CanvasLMS\Api\Outcomes\Outcome;
use CanvasLMS\Api\OutcomeGroups\OutcomeGroup;
// Create an outcome group
$group = OutcomeGroup::create([
'title' => 'Critical Thinking Skills',
'description' => 'Core competencies for analytical thinking'
]);
// Create a learning outcome
$outcome = Outcome::create([
'title' => 'Analyze Complex Problems',
'description' => 'Student can break down complex problems into manageable parts',
'mastery_points' => 3,
'ratings' => [
['description' => 'Exceeds', 'points' => 4],
['description' => 'Mastery', 'points' => 3],
['description' => 'Near Mastery', 'points' => 2],
['description' => 'Below Mastery', 'points' => 1]
]
]);
// Link outcome to a group
$group->linkOutcome($outcome->id);
// Align outcome with an assignment
$assignment = Assignment::find(123);
$assignment->alignOutcome($outcome->id, [
'mastery_score' => 3,
'possible_score' => 4
]);
use CanvasLMS\Api\Courses\Course;
use CanvasLMS\Api\ContentMigrations\ContentMigration;
// Copy content between courses
$course = Course::find(456);
$migration = $course->copyContentFrom(123, [
'except' => ['announcements', 'calendar_events']
]);
// Selective copy with specific items
$migration = $course->selectiveCopyFrom(123, [
'assignments' => [1, 2, 3],
'quizzes' => ['quiz-1', 'quiz-2'],
'modules' => [10, 11]
]);
// Import a Common Cartridge file
$migration = $course->importCommonCartridge('/path/to/course.imscc');
// Copy with date shifting
$migration = $course->copyWithDateShift(123, '2024-01-01', '2025-01-01', [
'shift_dates' => true,
'old_start_date' => '2024-01-01',
'new_start_date' => '2025-01-01'
]);
// Track migration progress
while (!$migration->isCompleted()) {
$progress = $migration->getProgress();
echo "Migration {$progress->workflow_state}: {$progress->completion}%\n";
sleep(5);
$migration->refresh();
}
// Handle migration issues
$issues = $migration->migrationIssues();
foreach ($issues as $issue) {
if ($issue->workflow_state === 'active') {
$issue->resolve();
}
}
// The SDK automatically handles rate limiting and retries
$course = Course::find(123); // Protected by middleware
// Canvas API Rate Limiting (3000 requests/hour)
// ✅ Automatic throttling when approaching limits
// ✅ Smart backoff strategies
// ✅ Transparent to your application
use CanvasLMS\Canvas;
// Follow pagination URLs returned by Canvas
$courses = Course::paginate();
while ($nextUrl = $courses->getNextUrl()) {
$nextPage = Canvas::get($nextUrl);
// Process next page data
}
// Call custom or undocumented endpoints
$analytics = Canvas::get('/api/v1/courses/123/analytics');
$customData = Canvas::post('/api/v1/custom/endpoint', [
'key' => 'value'
]);
// Download files directly
$file = File::find(456);
$content = Canvas::get($file->url);
file_put_contents('download.pdf', $content);
// Process webhook callbacks
$webhookData = json_decode($request->getContent(), true);
$resource = Canvas::get($webhookData['resource_url']);
// All HTTP methods supported
$response = Canvas::get($url); // GET request
$response = Canvas::post($url, $data); // POST request
$response = Canvas::put($url, $data); // PUT request
$response = Canvas::delete($url); // DELETE request
$response = Canvas::patch($url, $data); // PATCH request
$response = Canvas::request($url, 'HEAD'); // Any HTTP method
// Direct API calls use Account context (Config::getAccountId())
$groups = Group::get(); // First page of groups in the account
$allGroups = Group::all(); // All groups in the account
$rubrics = Rubric::get(); // First page of rubrics in the account
$migrations = ContentMigration::all(); // All migrations in the account
// Course-specific access via Course instance methods
$course = Course::find(123);
$courseGroups = $course->groups(); // Groups in this course
$courseRubrics = $course->rubrics(); // Rubrics in this course
$courseMigrations = $course->contentMigrations(); // Migrations in this course
// User-specific access via User instance methods
$user = User::find(456);
$userGroups = $user->groups(); // User's groups
$userMigrations = $user->contentMigrations(); // User's migrations
// Group-specific access via Group instance methods
$group = Group::find(789);
$groupMigrations = $group->contentMigrations(); // Group's migrations
Loading please wait ...
Before you can download the PHP files, the dependencies should be resolved. This can take some minutes. Please be patient.