Skip to content

Commit ce1044c

Browse files
committed
Merge branch 'core_integration' of github.com:rage/tmc-netbeans into core_integration
Conflicts: tmc-plugin/test/unit/src/fi/helsinki/cs/tmc/data/serialization/SubmissionResultParserTest.java
2 parents 47e93c8 + 9795649 commit ce1044c

File tree

8 files changed

+141
-101
lines changed

8 files changed

+141
-101
lines changed

tmc-plugin/src/fi/helsinki/cs/tmc/actions/CheckForUnopenedExercises.java

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
package fi.helsinki.cs.tmc.actions;
1+
package fi.helsinki.cs.tmc.actions;
22

33
import hy.tmc.core.domain.Exercise;
44
import fi.helsinki.cs.tmc.model.CourseDb;
Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
package fi.helsinki.cs.tmc.actions;
2+
3+
import com.google.common.util.concurrent.FutureCallback;
4+
import com.google.common.util.concurrent.Futures;
5+
import com.google.common.util.concurrent.ListenableFuture;
6+
import fi.helsinki.cs.tmc.data.FeedbackAnswer;
7+
8+
import fi.helsinki.cs.tmc.model.NBTmcSettings;
9+
import fi.helsinki.cs.tmc.model.TmcCoreSingleton;
10+
import fi.helsinki.cs.tmc.ui.ConvenientDialogDisplayer;
11+
import fi.helsinki.cs.tmc.utilities.ExceptionUtils;
12+
import hy.tmc.core.TmcCore;
13+
import hy.tmc.core.communication.HttpResult;
14+
import hy.tmc.core.domain.submission.SubmissionResult;
15+
import hy.tmc.core.exceptions.TmcCoreException;
16+
import java.io.IOException;
17+
import java.util.HashMap;
18+
import java.util.List;
19+
import java.util.Map;
20+
import java.util.logging.Level;
21+
import java.util.logging.Logger;
22+
import org.openide.util.Exceptions;
23+
24+
public class SendFeedbackAction {
25+
26+
private List<FeedbackAnswer> answers;
27+
private TmcCore core;
28+
private ConvenientDialogDisplayer dialogs;
29+
private final SubmissionResult result;
30+
private NBTmcSettings settings = NBTmcSettings.getDefault();
31+
private static final Logger log = Logger.getLogger(SendFeedbackAction.class.getName());
32+
33+
public SendFeedbackAction(List<FeedbackAnswer> answers, SubmissionResult result) {
34+
this.answers = answers;
35+
this.core = TmcCoreSingleton.getInstance();
36+
this.dialogs = ConvenientDialogDisplayer.getDefault();
37+
this.result = result;
38+
}
39+
40+
public void run() {
41+
try {
42+
ListenableFuture<HttpResult> feedbackFuture;
43+
feedbackFuture = core.sendFeedback(
44+
getFeedbackAnswers(), result.getFeedbackAnswerUrl(), settings
45+
);
46+
Futures.addCallback(feedbackFuture, new FeedbackReplyCallback());
47+
} catch (TmcCoreException ex) {
48+
Exceptions.printStackTrace(ex);
49+
} catch (IOException ex) {
50+
Exceptions.printStackTrace(ex);
51+
}
52+
}
53+
54+
private Map<String, String> getFeedbackAnswers() {
55+
Map<String, String> answerMap = new HashMap<String, String>();
56+
57+
for (FeedbackAnswer answer : answers) {
58+
answerMap.put("" + answer.getQuestion().getId(), answer.getAnswer());
59+
}
60+
61+
return answerMap;
62+
}
63+
64+
private class FeedbackReplyCallback implements FutureCallback<HttpResult> {
65+
66+
@Override
67+
public void onSuccess(HttpResult v) {
68+
System.out.println(v.getData() + " " + v.getStatusCode());
69+
}
70+
71+
@Override
72+
public void onFailure(Throwable ex) {
73+
String msg = "Failed to send feedback :-(\n" + ex.getMessage();
74+
String msgWithBacktrace = msg + "\n" + ExceptionUtils.backtraceToString(ex);
75+
log.log(Level.INFO, msgWithBacktrace);
76+
dialogs.displayError(msg);
77+
}
78+
}
79+
}

tmc-plugin/src/fi/helsinki/cs/tmc/actions/SubmitExerciseAction.java

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,8 +4,8 @@
44
import com.google.common.util.concurrent.Futures;
55
import com.google.common.util.concurrent.ListenableFuture;
66
import fi.helsinki.cs.tmc.data.ResultCollector;
7+
import fi.helsinki.cs.tmc.events.TmcEvent;
78
import fi.helsinki.cs.tmc.events.TmcEventBus;
8-
import fi.helsinki.cs.tmc.exerciseSubmitter.ExerciseSubmitter;
99

1010
import fi.helsinki.cs.tmc.model.CourseDb;
1111
import fi.helsinki.cs.tmc.model.NBTmcSettings;
@@ -37,6 +37,13 @@ public final class SubmitExerciseAction extends AbstractExerciseSensitiveAction
3737
private NBTmcSettings settings;
3838
private ConvenientDialogDisplayer dialogs;
3939

40+
public static class InvokedEvent implements TmcEvent {
41+
public final TmcProjectInfo projectInfo;
42+
public InvokedEvent(TmcProjectInfo projectInfo) {
43+
this.projectInfo = projectInfo;
44+
}
45+
}
46+
4047
public SubmitExerciseAction() {
4148
this.courseDb = CourseDb.getInstance();
4249
this.projectMediator = ProjectMediator.getInstance();
@@ -65,7 +72,7 @@ protected void performAction(Node[] nodes) {
6572
Project[] projects = projectsFromNodes(nodes).toArray(new Project[0]);
6673
for (Project project : projects) {
6774
TmcProjectInfo info = projectMediator.wrapProject(project);
68-
TmcEventBus.getDefault().post(new ExerciseSubmitter.InvokedEvent(info));
75+
TmcEventBus.getDefault().post(new SubmitExerciseAction.InvokedEvent(info));
6976
submitProject(info);
7077
}
7178
}
Lines changed: 45 additions & 69 deletions
Original file line numberDiff line numberDiff line change
@@ -1,112 +1,88 @@
11
package fi.helsinki.cs.tmc.actions;
22

3+
import com.google.common.util.concurrent.FutureCallback;
4+
import com.google.common.util.concurrent.Futures;
5+
import com.google.common.util.concurrent.ListenableFuture;
36
import hy.tmc.core.domain.Exercise;
47
import fi.helsinki.cs.tmc.model.CourseDb;
5-
import fi.helsinki.cs.tmc.model.ExerciseUpdateOverwritingDecider;
8+
import fi.helsinki.cs.tmc.model.NBTmcSettings;
69
import fi.helsinki.cs.tmc.model.ProjectMediator;
710
import fi.helsinki.cs.tmc.model.ServerAccess;
11+
import fi.helsinki.cs.tmc.model.TmcCoreSingleton;
812
import fi.helsinki.cs.tmc.model.TmcProjectInfo;
913
import fi.helsinki.cs.tmc.ui.ConvenientDialogDisplayer;
10-
import fi.helsinki.cs.tmc.utilities.AggregatingBgTaskListener;
11-
import fi.helsinki.cs.tmc.utilities.BgTask;
12-
import fi.helsinki.cs.tmc.utilities.BgTaskListener;
13-
import fi.helsinki.cs.tmc.utilities.zip.NbProjectUnzipper;
14+
import hy.tmc.core.TmcCore;
15+
import hy.tmc.core.exceptions.TmcCoreException;
1416
import java.awt.event.ActionEvent;
1517
import java.awt.event.ActionListener;
16-
import java.io.File;
17-
import java.io.IOException;
1818
import java.util.ArrayList;
19-
import java.util.Collection;
2019
import java.util.List;
2120
import java.util.logging.Logger;
21+
import org.openide.util.Exceptions;
2222

2323
public class UpdateExercisesAction implements ActionListener {
24-
24+
2525
private static final Logger log = Logger.getLogger(UpdateExercisesAction.class.getName());
2626

2727
private List<Exercise> exercisesToUpdate;
2828
private CourseDb courseDb;
2929
private ProjectMediator projectMediator;
3030
private ServerAccess serverAccess;
3131
private ConvenientDialogDisplayer dialogDisplayer;
32-
32+
private TmcCore core;
33+
3334
public UpdateExercisesAction(List<Exercise> exercisesToUpdate) {
3435
this.exercisesToUpdate = exercisesToUpdate;
3536
this.courseDb = CourseDb.getInstance();
3637
this.projectMediator = ProjectMediator.getInstance();
3738
this.serverAccess = new ServerAccess();
3839
this.dialogDisplayer = ConvenientDialogDisplayer.getDefault();
40+
this.core = TmcCoreSingleton.getInstance();
3941
}
4042

4143
@Override
4244
public void actionPerformed(ActionEvent e) {
4345
run();
4446
}
45-
47+
4648
public void run() {
47-
final AggregatingBgTaskListener<TmcProjectInfo> projectOpener = new AggregatingBgTaskListener<TmcProjectInfo>(exercisesToUpdate.size(), new BgTaskListener<Collection<TmcProjectInfo>>() {
48-
@Override
49-
public void bgTaskReady(Collection<TmcProjectInfo> result) {
50-
result = new ArrayList<TmcProjectInfo>(result);
51-
52-
// result may contain nulls since some downloads might fail
53-
while (result.remove(null)) {
54-
}
55-
56-
projectMediator.scanForExternalChanges(result);
57-
58-
// Open all at once. This is much faster.
59-
projectMediator.openProjects(result);
60-
}
61-
62-
// Cancelled and failed are never called since we only call bgTaskReady below manually
63-
@Override
64-
public void bgTaskCancelled() {
65-
}
66-
@Override
67-
public void bgTaskFailed(Throwable ex) {
68-
}
69-
});
70-
71-
72-
for (final Exercise exercise : exercisesToUpdate) {
73-
final File projectDir = projectMediator.getProjectDirForExercise(exercise);
49+
if (exercisesToUpdate.isEmpty()) {
50+
return;
51+
}
52+
try {
53+
ListenableFuture<List<Exercise>> downloadFuture = core.downloadExercises(exercisesToUpdate,
54+
NBTmcSettings.getDefault());
55+
Futures.addCallback(downloadFuture, new ProjectOpenerCallback());
7456

75-
BgTask.start("Downloading " + exercise.getName(), serverAccess.getDownloadingExerciseZipTask(exercise), new BgTaskListener<byte[]>() {
57+
} catch (TmcCoreException ex) {
58+
Exceptions.printStackTrace(ex);
59+
dialogDisplayer.displayError("Error occured while downloading updates", ex);
60+
}
61+
}
7662

77-
@Override
78-
public void bgTaskReady(byte[] data) {
79-
TmcProjectInfo project = null;
80-
try {
81-
try {
82-
ExerciseUpdateOverwritingDecider overwriter = new ExerciseUpdateOverwritingDecider(projectDir);
83-
NbProjectUnzipper unzipper = new NbProjectUnzipper(overwriter);
84-
NbProjectUnzipper.Result result = unzipper.unzipProject(data, projectDir);
85-
log.info("== Exercise unzip result ==\n" + result);
86-
} catch (IOException ex) {
87-
dialogDisplayer.displayError("Failed to update project.", ex);
88-
return;
89-
}
90-
courseDb.exerciseDownloaded(exercise);
91-
92-
project = projectMediator.tryGetProjectForExercise(exercise);
93-
} finally {
94-
projectOpener.bgTaskReady(project);
95-
}
96-
}
63+
private class ProjectOpenerCallback implements FutureCallback<List<Exercise>> {
9764

98-
@Override
99-
public void bgTaskCancelled() {
100-
projectOpener.bgTaskReady(null);
101-
}
65+
@Override
66+
public void onSuccess(List<Exercise> downloadedExercises) {
67+
ArrayList<TmcProjectInfo> projects = new ArrayList<TmcProjectInfo>();
10268

103-
@Override
104-
public void bgTaskFailed(Throwable ex) {
105-
projectOpener.bgTaskReady(null);
106-
String msg = ServerErrorHelper.getServerExceptionMsg(ex);
107-
dialogDisplayer.displayError("Failed to download updated exercises.\n" + msg, ex);
69+
for (Exercise exercise : downloadedExercises) {
70+
courseDb.exerciseDownloaded(exercise);
71+
TmcProjectInfo project = projectMediator.tryGetProjectForExercise(exercise);
72+
if (project != null) {
73+
projects.add(project);
10874
}
109-
});
75+
}
76+
projectMediator.scanForExternalChanges(projects);
77+
78+
projectMediator.openProjects(projects);
11079
}
80+
81+
@Override
82+
public void onFailure(Throwable ex) {
83+
Exceptions.printStackTrace(ex);
84+
dialogDisplayer.displayError("Error occured while downloading updates", ex);
85+
}
86+
11187
}
11288
}

tmc-plugin/src/fi/helsinki/cs/tmc/exerciseSubmitter/ExerciseSubmitter.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@
3030

3131
import org.netbeans.api.project.Project;
3232

33+
@Deprecated
3334
public class ExerciseSubmitter {
3435

3536
private static final Logger log = Logger.getLogger(SubmitExerciseAction.class.getName());

tmc-plugin/src/fi/helsinki/cs/tmc/runners/TestRunHandler.java

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
package fi.helsinki.cs.tmc.runners;
22

3-
import static fi.helsinki.cs.tmc.langs.RunResult.Status.COMPILE_FAILED;
3+
import static fi.helsinki.cs.tmc.langs.domain.RunResult.Status.COMPILE_FAILED;
44

55
import com.google.common.base.Throwables;
66
import com.google.common.collect.ImmutableList;
@@ -13,8 +13,9 @@
1313
import fi.helsinki.cs.tmc.events.TmcEvent;
1414
import fi.helsinki.cs.tmc.events.TmcEventBus;
1515
import fi.helsinki.cs.tmc.exerciseSubmitter.ExerciseSubmitter;
16-
import fi.helsinki.cs.tmc.langs.RunResult;
17-
import fi.helsinki.cs.tmc.langs.TestResult;
16+
import fi.helsinki.cs.tmc.langs.domain.RunResult;
17+
import fi.helsinki.cs.tmc.langs.domain.TestResult;
18+
1819
import fi.helsinki.cs.tmc.model.CourseDb;
1920
import fi.helsinki.cs.tmc.model.NBTmcSettings;
2021
import fi.helsinki.cs.tmc.model.ProjectMediator;

tmc-plugin/src/fi/helsinki/cs/tmc/ui/TestResultDisplayer.java

Lines changed: 2 additions & 25 deletions
Original file line numberDiff line numberDiff line change
@@ -1,24 +1,18 @@
11
package fi.helsinki.cs.tmc.ui;
22

3+
import fi.helsinki.cs.tmc.actions.SendFeedbackAction;
34
import hy.tmc.core.domain.Exercise;
45
import fi.helsinki.cs.tmc.data.FeedbackAnswer;
56
import fi.helsinki.cs.tmc.data.ResultCollector;
67
import hy.tmc.core.domain.submission.SubmissionResult;
78
import fi.helsinki.cs.tmc.data.TestCaseResult;
8-
import fi.helsinki.cs.tmc.langs.TestResult;
9-
import fi.helsinki.cs.tmc.model.ServerAccess;
109
import fi.helsinki.cs.tmc.stylerunner.validation.Strategy;
11-
import fi.helsinki.cs.tmc.utilities.BgTask;
12-
import fi.helsinki.cs.tmc.utilities.BgTaskListener;
13-
import fi.helsinki.cs.tmc.utilities.CancellableCallable;
14-
import fi.helsinki.cs.tmc.utilities.ExceptionUtils;
1510
import hy.tmc.core.domain.submission.TestCase;
1611
import java.awt.Dialog;
1712
import java.awt.event.ActionEvent;
1813
import java.awt.event.ActionListener;
1914
import java.util.ArrayList;
2015
import java.util.List;
21-
import java.util.logging.Level;
2216
import java.util.logging.Logger;
2317
import org.apache.commons.lang3.StringEscapeUtils;
2418
import org.apache.commons.lang3.StringUtils;
@@ -76,24 +70,7 @@ private void displaySuccessfulSubmissionMsg(Exercise exercise, final SubmissionR
7670
public void actionPerformed(ActionEvent e) {
7771
List<FeedbackAnswer> answers = dialog.getFeedbackAnswers();
7872
if (!answers.isEmpty()) {
79-
CancellableCallable<String> task = new ServerAccess().getFeedbackAnsweringJob(result.getFeedbackAnswerUrl(), answers);
80-
BgTask.start("Sending feedback", task, new BgTaskListener<String>() {
81-
@Override
82-
public void bgTaskReady(String result) {
83-
}
84-
85-
@Override
86-
public void bgTaskCancelled() {
87-
}
88-
89-
@Override
90-
public void bgTaskFailed(Throwable ex) {
91-
String msg = "Failed to send feedback :-(\n" + ex.getMessage();
92-
String msgWithBacktrace = msg + "\n" + ExceptionUtils.backtraceToString(ex);
93-
log.log(Level.INFO, msgWithBacktrace);
94-
dialogs.displayError(msg);
95-
}
96-
});
73+
new SendFeedbackAction(answers, result).run();
9774
}
9875
}
9976
});

tmc-plugin/test/unit/src/fi/helsinki/cs/tmc/data/serialization/SubmissionResultParserTest.java

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -72,7 +72,6 @@ public void testExceptions() {
7272
String input = "{status: \"fail\", test_cases: " + testCasesJson + ", points: []}";
7373

7474
SubmissionResult result = parse(input);
75-
7675
TestException cex = result.getTestCases().get(0).getException();
7776
assertNotNull(cex);
7877
assertEquals("FooEx", cex.getClassName());

0 commit comments

Comments
 (0)