Skip to content

Commit 9b4b9f4

Browse files
coder6583Futurecomputerfixer20wildmanjKesterTanjhs-panda
authored
Permission Model + Image Builder (#2325)
* implemented a file system permission cleaner and hooked it up in each web api function to enforce it * auto infer group name from path * modify ssh * fix to test on gamma * Implement SSH key management and Unix user/group system - Add SshKey model with validation and fingerprinting - Implement UnixGroupManager service for user/group management - Create Unix users/groups automatically on course/staff creation - Add SSH key provisioning to authorized_keys - Implement FilesystemEnforcer with group-based permissions - Add SSH key management UI (restricted to staff/instructors) - Fix require paths for services in controllers - Add services directory to autoload paths - Create bootstrap script for existing courses - Add host system user setup scripts - Support BusyBox useradd (use -p '*' instead of --disabled-password) - Add comprehensive setup and testing scripts * testing * add a new daemon container * fix bugs * fix bugs ++ * add hint for ssh key creation * add symlink * testing ec2, add support on autolab side * Filesystem mapping + EC2 autograder changes * fix group * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * add support for EC2 settings in Autolab * fix issue with autograder initialization * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * fix groupa * editing ssh commands * added service user to classes * attempt to fix course permissions * unix file system scanner * install assessment * Revert "install assessment" This reverts commit 224f4ee. * Revert "unix file system scanner" This reverts commit 73326f8. * Revert "attempt to fix course permissions" This reverts commit 18d9fa4. * make user9999 always an instructor * test adding user9999 to all groups * remove integration bundle * fix user groups * remove check of local membership * fix script to have both local and group * tranfer ownership script * CAs should not be able to ssh * Add clarification about course unix group inclusions. * modify ssh commands * add provision and deprovision of keys * prevent group add error * fix typo in ssh commands * fixed ca and instructor ssh perms * sponsors and contact us page * try to add both app and user9999 * list dir to unix ops * fix unix ops delegation * change delegate parsing * mkdir over to unixops * formatting * should delegate during perm error * restrict dump yaml * yaml read file delegate to unix ops * is file delagated to unix ops * dump yaml to delegate * conversion of pathname * load config to delegate * guard against empty file read from delegate * try reload config file with fallback * handin directory exists delegate * bulk email and delegation of read writeup * delegate submission to unix ops * unable to read files and submit files * Submission unviewable * check if use_access_key exists * basic controller done, before tango integration * test modified symlink * try test modified symlink fix * update permissions when ssh key changes/user role changes * add cleanup step for symlinks * try fix symlink * add log statement to debug * modify unix_ops_daemon * test file transfer change * undo prev changes * try new change * revert changes * test new change * try new fix * try new fix * try new fix * fix circular dependency * try to fix for all except admin * remove user's directory once it has no courses * handle cleanup for deleted users * reverse unix group deletion * change symbolic link ownership * try to fix cd update issue * try to fix cd update issue * fix circular looping * try to fix circular looping * fix file access * undo file access changes * creating container image works * table UI almost done * refresh status implemented * make rails DB source of truth * refresh all status when reloading the page/ added refresh all button * access key * attempt to fix file perms * instance type guards * fixed migrations * logs get updated * format error * create parents if it does not exist * course creation delegate * rb sys delegate * list dir paths to delegate * fallback to list_dir for path exists * fix for view submission * fix view for submissions controller * delegate reading to unix * more archive read paths to be delagted * fix file manager * delete feedback and path access fallbacks * delegate delete and move to unix ops * add delete and move path to unix ops * only show ssh part if instructor * try modifying users list breadcrumb * modify "Users List" view to look the same as when it has a link * modify symlinks to handle admin properly * can view log now * additional details for uploading job * fallback for tango upload * allow for non empty feedback without autograder * autograding works with ec2docker now! * manage autograder images on manage course * debugging for autograding feedback * delegated write of feedback to unix ops * view feedback delegate * add description clarification * more unix ops delegation and documentation * fix autograder upload errors * debugging for saving autograder * autograder length increased * delegate list assessment dirs * upload uses delegate * disallow duplicate keys across all users * distinguish between duplicates for current user and copies from other users * Filter out non-ready container images in autograder settings and add … (#2322) Filter out non-ready container images in autograder settings and add dockerfile_contents column * remove ssh access for user once account deleted (keep unix account on system) * revert change * added admin container images controller + routes * add logic to wipe ssh access once account deleted * added template for managing images * added template for viewing build log * added template for new image page * try to prevent unix account creation for tas * created admin pages * new image form works now * can manage images with correct permissions now * public images have unique names * add public_template_id to container_images * can select public templates now * admin controller names don't overlap anymore * admin controller names don't overlap anymore, routes * passes base docker image tag and uri to tango * building image works without public template now * authorized false by default * only show container images that belong to the course * gemfile dockerfile update * added button to the manage public templates page * Fixed polling issue with ECR builder (#2323) * export delegate * order images in newly created order * add unique unix_user column to users table * fixed public_template.image_uri * attempt to fix non-unique ssh login issue * instructors can choose public images now * fixed bug with join * push unix_user database migration file * load dir to tar to delegate * lint fix * course directory name * change ruby version * clean up lint issues * clean up lint issues * changed production.rb template to add ec2_docker * added helper text to new docker image form * increase client max body in nginx * remove name index * debugging for admin ssh key * added prefix to unix group * remove t2 nano --------- Co-authored-by: Haoyu Yang <haoyuy@andrew.cmu.edu> Co-authored-by: Joey Wildman <josephwildman88@gmail.com> Co-authored-by: Kester <kestertan040@gmail.com> Co-authored-by: Joy Song <joys@andrew.cmu.edu> Co-authored-by: Giancarlo Umberto Ambrosino <129298577+Giabbi@users.noreply.github.com> Co-authored-by: Ubuntu <ubuntu@ip-172-31-84-53.ec2.internal>
1 parent e098031 commit 9b4b9f4

92 files changed

Lines changed: 7378 additions & 762 deletions

File tree

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

.ruby-version

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
3.2.2
1+
3.2.10

Dockerfile

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77
# https://github.com/phusion/passenger-docker
88
#
99
#
10-
FROM phusion/passenger-ruby32:2.6.1
10+
FROM phusion/passenger-ruby32:3.1.6
1111

1212
MAINTAINER Autolab Development Team "autolab-dev@andrew.cmu.edu"
1313

Gemfile

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
source 'https://rubygems.org'
2-
ruby '3.2.2'
2+
ruby '3.2.10'
33

44
gem 'rails', '=6.1.7.6'
55

@@ -179,4 +179,4 @@ gem 'uri', '0.10.3'
179179
gem 'friendly_id', '~> 5.5.0'
180180

181181
# to sanitize CSV files
182-
gem 'csv-safe'
182+
gem 'csv-safe'

Gemfile.lock

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -548,7 +548,7 @@ DEPENDENCIES
548548
yard
549549

550550
RUBY VERSION
551-
ruby 3.2.2p53
551+
ruby 3.2.10p266
552552

553553
BUNDLED WITH
554554
2.5.3

README.md

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -113,7 +113,6 @@ Autolab is released under the [Apache License 2.0](http://opensource.org/license
113113

114114
Please feel free to use Autolab at your school/organization. If you run into any problems, you can reach the core developers at `autolab-dev@andrew.cmu.edu` and we would be happy to help. On a case-by-case basis, we also provide servers for free. (Especially if you are an NGO or small high-school classroom)
115115

116-
117116
## Changelog
118117

119118
### [v3.0.0](https://github.com/autolab/Autolab/releases/tag/v3.0.0) (2024/07/24) UI-based deployment configuration, Simple File Manager, Export / Import Course, Tango, Grading Improvements

app/assets/javascripts/file_manager.js

Lines changed: 27 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,7 @@ function rename(path) {
55
$.ajax({
66
url: "/file_manager/" + rel_path,
77
type: "PUT",
8-
data: { new_name: new_name, relative_path: rel_path},
8+
data: { new_name: new_name, relative_path: rel_path },
99
success: function(data) {
1010
console.log(`Renamed: ${rel_path}`)
1111
location.reload();
@@ -19,12 +19,21 @@ function deleteSelected(path) {
1919
$.ajax({
2020
url: path,
2121
type: "DELETE",
22-
success: function () {
22+
dataType: "json",
23+
headers: {
24+
"Accept": "application/json"
25+
},
26+
success: function(response) {
27+
if (response && response.success === false) {
28+
reject(response.error || "Delete failed");
29+
return;
30+
}
2331
console.log(`Deleted: ${path}`);
2432
resolve();
2533
},
26-
error: function (xhr, status, error) {
27-
reject(error);
34+
error: function(xhr, status, error) {
35+
const message = (xhr && xhr.responseJSON && xhr.responseJSON.error) ? xhr.responseJSON.error : error;
36+
reject(message);
2837
}
2938
});
3039
})
@@ -38,7 +47,7 @@ function downloadSelected(path) {
3847
data: {
3948
path: path
4049
},
41-
success: function (data) {
50+
success: function(data) {
4251
let blob = new Blob([data], { type: 'application/x-tar' });
4352
let url = URL.createObjectURL(blob);
4453
let a = document.createElement('a');
@@ -53,7 +62,7 @@ function downloadSelected(path) {
5362
console.log(`Downloaded: ${data.filename}`);
5463
resolve();
5564
},
56-
error: function (xhr, status, error) {
65+
error: function(xhr, status, error) {
5766
console.error(`Failed to download ${path}: ${error}`);
5867
reject(error);
5968
}
@@ -76,11 +85,11 @@ function uploadFile(file, path, name) {
7685
data: formData,
7786
contentType: false,
7887
processData: false,
79-
success: function () {
88+
success: function() {
8089
console.log("Uploaded file successfully");
8190
resolve();
8291
},
83-
error: function (xhr, status, error) {
92+
error: function(xhr, status, error) {
8493
console.error(`Failed to upload file: ${error}`);
8594
reject(error);
8695
}
@@ -98,14 +107,14 @@ function uploadAllFiles(path) {
98107
}
99108
if (files.length > 0) {
100109
Promise.all(uploadPromises)
101-
.then(() => {
102-
alert("All files uploaded successfully.");
103-
location.reload();
104-
})
105-
.catch((error) => {
106-
alert("Some files failed to upload successfully. Ensure that you are not in the root directory, the file is smaller than 1 GB, and does not already exist.");
107-
location.reload();
108-
});
110+
.then(() => {
111+
alert("All files uploaded successfully.");
112+
location.reload();
113+
})
114+
.catch((error) => {
115+
alert("Some files failed to upload successfully. Ensure that you are not in the root directory, the file is smaller than 1 GB, and does not already exist.");
116+
location.reload();
117+
});
109118
} else {
110119
console.log('No files selected.');
111120
}
@@ -130,8 +139,7 @@ function createFolder(path) {
130139
})
131140
.catch((error) => {
132141
alert("Failed to create folder. Check that you are not in the root directory and that the tile/folder does not already exist.");
133-
})
134-
;
142+
});
135143
}
136144
}
137145

@@ -219,4 +227,4 @@ document.addEventListener('DOMContentLoaded', function() {
219227
$(".check").click(function() {
220228
handleSelectionChange();
221229
})
222-
});
230+
});
Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,10 @@
1+
.contact-page {
2+
.contact-card .card-content .card-title {
3+
display: flex;
4+
align-items: center;
5+
gap: 0.2rem;
6+
}
7+
.contact-card .card-content .card-title .contact-icon {
8+
font-size: 1.5rem;
9+
}
10+
}
Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,8 @@
11
/* For the materialize gem documentation, check out https://github.com/mkhairi/materialize-sass */
2+
23
$primary-color: #dd2222 !default;
34
$secondary-color: #dd2222 !default;
45
@import "materialize";
56
@import "bootstrap-sprockets";
6-
@import "bootstrap-datetimepicker";
7+
@import "bootstrap-datetimepicker";
8+
@import "contact";
Lines changed: 9 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,20 @@
11
@import 'variables';
2-
32
.badge {
4-
&.blue {
5-
margin-left: 0 !important;
6-
}
3+
&.blue {
4+
margin-left: 0 !important;
5+
}
76
}
87

98
.card-title {
10-
margin-bottom: 0 !important;
9+
margin-bottom: 0 !important;
1110
}
1211

1312
.hover p {
14-
display: none;
13+
display: none;
1514
}
1615

1716
.collection-item:hover {
18-
.hover {
19-
display: block;
20-
}
21-
}
17+
.hover {
18+
display: block;
19+
}
20+
}
Lines changed: 139 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,139 @@
1+
.status-cell {
2+
font-size: 18px;
3+
}
4+
5+
.material-icons.status-icon {
6+
font-size: 24px;
7+
}
8+
9+
.center-column {
10+
height: 100%;
11+
border: 0;
12+
outline: 0;
13+
display: flex;
14+
flex-direction: column;
15+
justify-content: center;
16+
align-content: center;
17+
}
18+
19+
.log-link {
20+
font-size: 14px;
21+
display: flex;
22+
justify-content: center;
23+
align-content: center;
24+
}
25+
26+
.all-icon {
27+
display: flex;
28+
justify-content: center;
29+
align-content: center;
30+
}
31+
32+
.error-icon {
33+
color: red;
34+
}
35+
36+
.hourglass-icon {
37+
color: lightgray;
38+
}
39+
40+
.draft-icon {
41+
color: gray;
42+
}
43+
44+
.building-icon {
45+
color: gray;
46+
}
47+
48+
.success-icon {
49+
color: limegreen;
50+
}
51+
52+
.source-table {
53+
margin-bottom: 36px;
54+
}
55+
56+
.mr-8 {
57+
margin-right: 8px;
58+
}
59+
60+
.status-chip {
61+
display: inline-flex;
62+
align-items: center;
63+
gap: 0.35rem;
64+
65+
padding: 0.2rem 0.5rem;
66+
border: 1px solid currentColor;
67+
border-radius: 0.2rem;
68+
69+
font-size: 1rem;
70+
font-weight: 500;
71+
line-height: 1.2;
72+
white-space: nowrap;
73+
}
74+
75+
.status-chip__icon {
76+
display: inline-flex;
77+
align-items: center;
78+
justify-content: center;
79+
width: 0.8rem;
80+
height: 0.8rem;
81+
flex-shrink: 0;
82+
}
83+
84+
.status-chip--draft {
85+
color: #d9534f;
86+
background-color: #fdf1f1;
87+
}
88+
89+
.status-chip--building {
90+
color: #21b5b0;
91+
background-color: #eefbfa;
92+
}
93+
94+
.status-chip--ready {
95+
color: limegreen;
96+
background-color: #f1fdf1;
97+
}
98+
99+
.status-chip--disabled {
100+
color: gray;
101+
background-color: #fdfdfd;
102+
}
103+
104+
.status-chip--error {
105+
color: #8A0000;
106+
background-color: #f8f1f1;
107+
}
108+
109+
.tooltip {
110+
position: relative;
111+
display: inline-block;
112+
cursor: pointer;
113+
}
114+
115+
.tooltip-hover {
116+
visibility: hidden;
117+
opacity: 0;
118+
119+
position: absolute;
120+
bottom: 125%;
121+
left: 50%;
122+
transform: translateX(-50%);
123+
124+
background-color: #333;
125+
color: #fff;
126+
padding: 6px 8px;
127+
border-radius: 4px;
128+
129+
font-size: 0.75rem;
130+
white-space: nowrap;
131+
132+
transition: opacity 0.2s;
133+
z-index: 10;
134+
}
135+
136+
.tooltip:hover .tooltip-hover {
137+
visibility: visible;
138+
opacity: 1;
139+
}

0 commit comments

Comments
 (0)