Skip to content

Commit

Permalink
Store the build path used in Sketch
Browse files Browse the repository at this point in the history
Previously, everywhere where it was needed, the path was requested from
BaseNoGui. Because the path is based on a hash of the sketch filename,
every caller would get the same path for the same sketch.

However, it makes more sense to store the path used for a given sketch
inside the Sketch object. This prevents having to pass around or
regenerate the build path everywhere, and no longer requires the build
path to be deterministic (though it still is in this commit).

This allows removing some methods and constructors of which two versions
were available - one with a build path argument and one without.
  • Loading branch information
matthijskooijman authored and facchinm committed Aug 26, 2016
1 parent c4e77a7 commit 4f0af2a
Show file tree
Hide file tree
Showing 5 changed files with 50 additions and 78 deletions.
60 changes: 8 additions & 52 deletions app/src/processing/app/SketchController.java
Expand Up @@ -253,7 +253,7 @@ public void handleDeleteCode() throws IOException {
editor.base.handleClose(editor);
} else {
// delete the file
if (!current.delete(BaseNoGui.getBuildFolder(sketch).toPath())) {
if (!current.delete(sketch.getBuildPath().toPath())) {
Base.showMessage(tr("Couldn't do it"),
I18n.format(tr("Could not delete \"{0}\"."), current.getFileName()));
return;
Expand Down Expand Up @@ -614,43 +614,6 @@ public void importLibrary(UserLibrary lib) throws IOException {
editor.getCurrentTab().setSelection(0, 0); // scroll to start
}

/**
* Preprocess, Compile, and Run the current code.
* <P>
* There are three main parts to this process:
* <PRE>
* (0. if not java, then use another 'engine'.. i.e. python)
*
* 1. do the p5 language preprocessing
* this creates a working .java file in a specific location
* better yet, just takes a chunk of java code and returns a
* new/better string editor can take care of saving this to a
* file location
*
* 2. compile the code from that location
* catching errors along the way
* placing it in a ready classpath, or .. ?
*
* 3. run the code
* needs to communicate location for window
* and maybe setup presentation space as well
* run externally if a code folder exists,
* or if more than one file is in the project
*
* X. afterwards, some of these steps need a cleanup function
* </PRE>
*/
//protected String compile() throws RunnerException {

/**
* Run the build inside the temporary build folder.
* @return null if compilation failed, main class name if not
* @throws RunnerException
*/
public String build(boolean verbose, boolean save) throws RunnerException, PreferencesMapException, IOException {
return build(BaseNoGui.getBuildFolder(sketch).getAbsolutePath(), verbose, save);
}

/**
* Preprocess and compile all the code for this sketch.
*
Expand All @@ -660,7 +623,7 @@ public String build(boolean verbose, boolean save) throws RunnerException, Prefe
*
* @return null if compilation failed, main class name if not
*/
private String build(String buildPath, boolean verbose, boolean save) throws RunnerException, PreferencesMapException, IOException {
public String build(boolean verbose, boolean save) throws RunnerException, PreferencesMapException, IOException {
// run the preprocessor
editor.status.progressUpdate(20);

Expand All @@ -678,7 +641,7 @@ private String build(String buildPath, boolean verbose, boolean save) throws Run
}

try {
return new Compiler(pathToSketch, sketch, buildPath).build(progressListener, save);
return new Compiler(pathToSketch, sketch).build(progressListener, save);
} finally {
// Make sure we clean up any temporary sketch copy
if (deleteTemp)
Expand All @@ -697,20 +660,13 @@ private File saveSketchInTempFolder() throws IOException {
return Paths.get(tempFolder.getAbsolutePath(), sketch.getPrimaryFile().getFileName()).toFile();
}

protected boolean exportApplet(boolean usingProgrammer) throws Exception {
return exportApplet(BaseNoGui.getBuildFolder(sketch).getAbsolutePath(), usingProgrammer);
}


/**
* Handle export to applet.
*/
private boolean exportApplet(String appletPath, boolean usingProgrammer)
throws Exception {

protected boolean exportApplet(boolean usingProgrammer) throws Exception {
// build the sketch
editor.status.progressNotice(tr("Compiling sketch..."));
String foundName = build(appletPath, false, false);
String foundName = build(false, false);
// (already reported) error during export, exit this function
if (foundName == null) return false;

Expand All @@ -724,12 +680,12 @@ private boolean exportApplet(String appletPath, boolean usingProgrammer)
// }

editor.status.progressNotice(tr("Uploading..."));
boolean success = upload(appletPath, foundName, usingProgrammer);
boolean success = upload(foundName, usingProgrammer);
editor.status.progressUpdate(100);
return success;
}

private boolean upload(String buildPath, String suggestedClassName, boolean usingProgrammer) throws Exception {
private boolean upload(String suggestedClassName, boolean usingProgrammer) throws Exception {

UploaderUtils uploaderInstance = new UploaderUtils();
Uploader uploader = uploaderInstance.getUploaderByPreferences(false);
Expand All @@ -751,7 +707,7 @@ private boolean upload(String buildPath, String suggestedClassName, boolean usin

List<String> warningsAccumulator = new LinkedList<>();
try {
success = uploaderInstance.upload(sketch, uploader, buildPath, suggestedClassName, usingProgrammer, false, warningsAccumulator);
success = uploaderInstance.upload(sketch, uploader, suggestedClassName, usingProgrammer, false, warningsAccumulator);
} finally {
if (uploader.requiresAuthorization() && !success) {
PreferencesData.remove(uploader.getAuthorizationKey());
Expand Down
11 changes: 6 additions & 5 deletions arduino-core/src/cc/arduino/Compiler.java
Expand Up @@ -112,22 +112,23 @@ enum BuilderAction {

private final File pathToSketch;
private final Sketch sketch;
private final String buildPath;
private String buildPath;
private final boolean verbose;
private RunnerException exception;

public Compiler(Sketch data, String buildPath) {
this(data.getPrimaryFile().getFile(), data, buildPath);
public Compiler(Sketch data) {
this(data.getPrimaryFile().getFile(), data);
}

public Compiler(File pathToSketch, Sketch sketch, String buildPath) {
public Compiler(File pathToSketch, Sketch sketch) {
this.pathToSketch = pathToSketch;
this.sketch = sketch;
this.buildPath = buildPath;
this.verbose = PreferencesData.getBoolean("build.verbose");
}

public String build(CompilerProgressListener progListener, boolean exportHex) throws RunnerException, PreferencesMapException, IOException {
this.buildPath = sketch.getBuildPath().getAbsolutePath();

TargetBoard board = BaseNoGui.getTargetBoard();
if (board == null) {
throw new RunnerException("Board is not selected");
Expand Down
4 changes: 2 additions & 2 deletions arduino-core/src/cc/arduino/UploaderUtils.java
Expand Up @@ -56,7 +56,7 @@ public Uploader getUploaderByPreferences(boolean noUploadPort) {
return new UploaderFactory().newUploader(target.getBoards().get(board), boardPort, noUploadPort);
}

public boolean upload(Sketch data, Uploader uploader, String buildPath, String suggestedClassName, boolean usingProgrammer, boolean noUploadPort, List<String> warningsAccumulator) throws Exception {
public boolean upload(Sketch data, Uploader uploader, String suggestedClassName, boolean usingProgrammer, boolean noUploadPort, List<String> warningsAccumulator) throws Exception {

if (uploader == null)
uploader = getUploaderByPreferences(noUploadPort);
Expand All @@ -75,7 +75,7 @@ public boolean upload(Sketch data, Uploader uploader, String buildPath, String s
}

try {
success = uploader.uploadUsingPreferences(data.getFolder(), buildPath, suggestedClassName, usingProgrammer, warningsAccumulator);
success = uploader.uploadUsingPreferences(data.getFolder(), data.getBuildPath().getAbsolutePath(), suggestedClassName, usingProgrammer, warningsAccumulator);
} finally {
if (uploader.requiresAuthorization() && !success) {
PreferencesData.remove(uploader.getAuthorizationKey());
Expand Down
22 changes: 3 additions & 19 deletions arduino-core/src/processing/app/BaseNoGui.java
Expand Up @@ -14,7 +14,6 @@
import cc.arduino.packages.DiscoveryManager;
import cc.arduino.packages.Uploader;
import com.fasterxml.jackson.core.JsonProcessingException;
import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.compress.utils.IOUtils;
import org.apache.commons.logging.impl.LogFactoryImpl;
import org.apache.commons.logging.impl.NoOpLog;
Expand All @@ -29,7 +28,6 @@
import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.nio.file.Files;
import java.util.*;
import java.util.logging.Level;
import java.util.logging.Logger;
Expand Down Expand Up @@ -124,18 +122,6 @@ static public String getAvrBasePath() {
return path;
}

static public File getBuildFolder(Sketch data) throws IOException {
File buildFolder;
if (PreferencesData.get("build.path") != null) {
buildFolder = absoluteFile(PreferencesData.get("build.path"));
Files.createDirectories(buildFolder.toPath());
} else {
buildFolder = FileUtils.createTempFolder("build", DigestUtils.md5Hex(data.getMainFilePath()) + ".tmp");
DeleteFilesOnShutdown.add(buildFolder);
}
return buildFolder;
}

static public PreferencesMap getBoardPreferences() {
TargetBoard board = getTargetBoard();
if (board == null)
Expand Down Expand Up @@ -508,7 +494,6 @@ static public void init(String[] args) throws Exception {
// SketchData data = new SketchData(file);
// File tempBuildFolder = getBuildFolder();
Sketch data = new Sketch(absoluteFile(parser.getFilenames().get(0)));
File tempBuildFolder = getBuildFolder(data);

// Sketch.exportApplet()
// - calls Sketch.prepare() that calls Sketch.ensureExistence()
Expand All @@ -517,7 +502,7 @@ static public void init(String[] args) throws Exception {
if (!data.getFolder().exists()) {
showError(tr("No sketch"), tr("Can't find the sketch in the specified path"), null);
}
String suggestedClassName = new Compiler(data, tempBuildFolder.getAbsolutePath()).build(null, false);
String suggestedClassName = new Compiler(data).build(null, false);
if (suggestedClassName == null) {
showError(tr("Error while verifying"), tr("An error occurred while verifying the sketch"), null);
}
Expand All @@ -526,7 +511,7 @@ static public void init(String[] args) throws Exception {
Uploader uploader = new UploaderUtils().getUploaderByPreferences(parser.isNoUploadPort());
if (uploader.requiresAuthorization() && !PreferencesData.has(uploader.getAuthorizationKey())) showError("...", "...", null);
try {
success = new UploaderUtils().upload(data, uploader, tempBuildFolder.getAbsolutePath(), suggestedClassName, parser.isDoUseProgrammer(), parser.isNoUploadPort(), warningsAccumulator);
success = new UploaderUtils().upload(data, uploader, suggestedClassName, parser.isDoUseProgrammer(), parser.isNoUploadPort(), warningsAccumulator);
showMessage(tr("Done uploading"), tr("Done uploading"));
} finally {
if (uploader.requiresAuthorization() && !success) {
Expand Down Expand Up @@ -554,15 +539,14 @@ static public void init(String[] args) throws Exception {
// File tempBuildFolder = getBuildFolder();
// data.load();
Sketch data = new Sketch(absoluteFile(path));
File tempBuildFolder = getBuildFolder(data);

// Sketch.prepare() calls Sketch.ensureExistence()
// Sketch.build(verbose) calls Sketch.ensureExistence() and set progressListener and, finally, calls Compiler.build()
// This translates here as:
// if (!data.getFolder().exists()) showError(...);
// String ... = Compiler.build(data, tempBuildFolder.getAbsolutePath(), tempBuildFolder, null, verbose);
if (!data.getFolder().exists()) showError(tr("No sketch"), tr("Can't find the sketch in the specified path"), null);
String suggestedClassName = new Compiler(data, tempBuildFolder.getAbsolutePath()).build(null, false);
String suggestedClassName = new Compiler(data).build(null, false);
if (suggestedClassName == null) showError(tr("Error while verifying"), tr("An error occurred while verifying the sketch"), null);
showMessage(tr("Done compiling"), tr("Done compiling"));
} catch (Exception e) {
Expand Down
31 changes: 31 additions & 0 deletions arduino-core/src/processing/app/Sketch.java
Expand Up @@ -2,10 +2,14 @@

import java.io.File;
import java.io.IOException;
import java.nio.file.Files;
import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.Stream;

import org.apache.commons.codec.digest.DigestUtils;

import cc.arduino.files.DeleteFilesOnShutdown;
import processing.app.helpers.FileUtils;

import static processing.app.I18n.tr;
Expand All @@ -27,6 +31,8 @@ public class Sketch {

private List<SketchFile> files = new ArrayList<SketchFile>();

private File buildPath;

private static final Comparator<SketchFile> CODE_DOCS_COMPARATOR = new Comparator<SketchFile>() {
@Override
public int compare(SketchFile x, SketchFile y) {
Expand Down Expand Up @@ -161,6 +167,31 @@ public SketchFile getFile(int i) {
return files.get(i);
}

/**
* Gets the build path for this sketch. The first time this is called,
* a build path is generated and created and the same path is returned
* on all subsequent calls.
*
* This takes into account the build.path preference. If it is set,
* that path is always returned, and the directory is *not* deleted on
* shutdown. If the preference is not set, a pathname in a
* temporary directory is generated, which is automatically deleted on
* shutdown.
*/
public File getBuildPath() throws IOException {
if (buildPath == null) {
if (PreferencesData.get("build.path") != null) {
buildPath = BaseNoGui.absoluteFile(PreferencesData.get("build.path"));
Files.createDirectories(buildPath.toPath());
} else {
buildPath = FileUtils.createTempFolder("build", DigestUtils.md5Hex(getMainFilePath()) + ".tmp");
DeleteFilesOnShutdown.add(buildPath);
}
}

return buildPath;
}

protected void removeFile(SketchFile which) {
if (!files.remove(which))
System.err.println("removeCode: internal error.. could not find code");
Expand Down

0 comments on commit 4f0af2a

Please sign in to comment.