bool copySourceFile(const FilePath& sourceDir, const FilePath& destDir, int level, const FilePath& sourceFilePath) { // compute the target path std::string relativePath = sourceFilePath.relativePath(sourceDir); FilePath targetPath = destDir.complete(relativePath); // if the copy item is a directory just create it if (sourceFilePath.isDirectory()) { Error error = targetPath.ensureDirectory(); if (error) LOG_ERROR(error); } // otherwise copy it else { Error error = sourceFilePath.copy(targetPath); if (error) LOG_ERROR(error); } return true; }
ExecuteChunkOperation(const std::string& docId, const std::string& chunkId, const std::string& nbCtxId, const ShellCommand& command, const core::FilePath& scriptPath) : terminationRequested_(false), docId_(docId), chunkId_(chunkId), nbCtxId_(nbCtxId), command_(command), scriptPath_(scriptPath) { using namespace core; Error error = Success(); // ensure regular directory FilePath outputPath = chunkOutputPath( docId_, chunkId_, ContextExact); error = outputPath.removeIfExists(); if (error) LOG_ERROR(error); error = outputPath.ensureDirectory(); if (error) LOG_ERROR(error); // clean old chunk output error = cleanChunkOutput(docId_, chunkId_, nbCtxId_, true); if (error) LOG_ERROR(error); }
FilePath getProjectUserDataDir(const ErrorLocation& location) { // get the project directory FilePath projectDir = projects::projectContext().directory(); // presume that the project dir is the data dir then check // for a .Ruserdata directory as an alternative FilePath dataDir = projectDir; FilePath ruserdataDir = projectDir.childPath(".Ruserdata"); if (ruserdataDir.exists()) { // create user-specific subdirectory if necessary FilePath userDir = ruserdataDir.childPath(core::system::username()); Error error = userDir.ensureDirectory(); if (!error) { dataDir = userDir; } else { core::log::logError(error, location); } } // return the data dir return dataDir; }
// IN: String sourcePath, String targetPath Error copyFile(const ::core::json::JsonRpcRequest& request, json::JsonRpcResponse* pResponse) { // read params std::string sourcePath, targetPath; bool overwrite; Error error = json::readParams(request.params, &sourcePath, &targetPath, &overwrite); if (error) return error; FilePath targetFilePath = module_context::resolveAliasedPath(targetPath); // make sure the target path doesn't exist if (targetFilePath.exists()) { if (overwrite) { Error error = targetFilePath.remove(); if (error) { LOG_ERROR(error); return fileExistsError(ERROR_LOCATION); } } else { return fileExistsError(ERROR_LOCATION); } } // compute the source file path FilePath sourceFilePath = module_context::resolveAliasedPath(sourcePath); // copy directories recursively Error copyError ; if (sourceFilePath.isDirectory()) { // create the target directory Error error = targetFilePath.ensureDirectory(); if (error) return error ; // iterate over the source copyError = sourceFilePath.childrenRecursive( boost::bind(copySourceFile, sourceFilePath, targetFilePath, _1, _2)); } else { copyError = sourceFilePath.copy(targetFilePath); } // check quota after copies quotas::checkQuotaStatus(); // return error status return copyError; }
FilePath historySerializationPath() { FilePath historyPath = module_context::sessionScratchPath() .childPath("viewer_history"); Error error = historyPath.ensureDirectory(); if (error) LOG_ERROR(error); return historyPath; }
FileLogWriter::FileLogWriter(const std::string& programIdentity, int logLevel, const FilePath& logDir) : programIdentity_(programIdentity), logLevel_(logLevel) { logDir.ensureDirectory(); logFile_ = logDir.childPath(programIdentity + ".log"); }
FilePath RestartContext::createSessionStatePath(const FilePath& scopePath, const std::string& contextId) { FilePath contextsPath = restartContextsPath(scopePath); FilePath statePath = contextsPath.complete(kContext + contextId); Error error = statePath.ensureDirectory(); if (error) LOG_ERROR(error); return statePath; }
inline Error initializeStreamDir(const FilePath& streamDir) { Error error = streamDir.ensureDirectory(); if (error) return error; error = changeFileMode(streamDir.parent(), system::EveryoneReadWriteExecuteMode); if (error) return error; return changeFileMode(streamDir, system::EveryoneReadWriteExecuteMode); }
FilePath userSettingsPath(const FilePath& userHomeDirectory, const std::string& appName) { std::string lower = appName; boost::to_lower(lower); FilePath path = userHomeDirectory.childPath("." + lower); Error error = path.ensureDirectory(); if (error) { LOG_ERROR(error); } return path; }
FileLogWriter::FileLogWriter(const std::string& programIdentity, int logLevel, const FilePath& logDir) : programIdentity_(programIdentity), logLevel_(logLevel) { logDir.ensureDirectory(); logFile_ = logDir.childPath(programIdentity + ".log"); if (!logFile_.exists()) { // swallow errors -- we can't log so it doesn't matter core::appendToFile(logFile_, ""); } }
FilePath viewInBrowserPath() { if (s_presentationState.viewInBrowserPath.empty()) { FilePath viewDir = module_context::tempFile("view", "dir"); Error error = viewDir.ensureDirectory(); if (!error) { s_presentationState.viewInBrowserPath = viewDir.childPath("presentation.html"); } else { LOG_ERROR(error); } } return s_presentationState.viewInBrowserPath; }
void initSaveContext(const FilePath& statePath, Settings* pSettings, bool* pSaved) { // ensure the context exists Error error = statePath.ensureDirectory(); if (error) { reportError(kSaving, "creating directory", error, ERROR_LOCATION); *pSaved = false; } // init session settings error = pSettings->initialize(statePath.complete(kSettingsFile)); if (error) { reportError(kSaving, kSettingsFile, error, ERROR_LOCATION); *pSaved = false; } }
// IN: String path core::Error createFolder(const core::json::JsonRpcRequest& request, json::JsonRpcResponse* pResponse) { std::string path; Error error = json::readParam(request.params, 0, &path); if (error) return error ; // create the directory FilePath folderPath = module_context::resolveAliasedPath(path) ; if (folderPath.exists()) { return fileExistsError(ERROR_LOCATION); } else { Error createError = folderPath.ensureDirectory() ; if (createError) return createError ; } return Success() ; }
void onDocSaved(FilePath &path) { Error error; // ignore non-R Markdown saves if (!path.hasExtensionLowerCase(".rmd")) return; // find cache folder (bail out if it doesn't exist) FilePath cache = chunkCacheFolder(path, "", notebookCtxId()); if (!cache.exists()) return; FilePath saved = chunkCacheFolder(path, "", kSavedCtx); if (saved.exists()) { // tidy up: remove any saved chunks that no longer exist error = removeStaleSavedChunks(path, saved); if (error) LOG_ERROR(error); } else { // no saved context yet; ensure we have a place to put it saved.ensureDirectory(); } // move all the chunk definitions over to the saved context std::vector<FilePath> children; error = cache.children(&children); if (error) { LOG_ERROR(error); return; } BOOST_FOREACH(const FilePath source, children) { // compute the target path FilePath target = saved.complete(source.filename()); if (source.filename() == kNotebookChunkDefFilename) { // the definitions should be copied (we always want them in both // contexts) error = target.removeIfExists(); if (!error) error = source.copy(target); } else if (source.isDirectory()) { // library folders should be merged and then removed, so we don't // lose library contents if (source.filename() == kChunkLibDir) { error = mergeLib(source, target); if (!error) error = source.remove(); } else { // the chunk output folders should be moved; destroy the old copy error = target.removeIfExists(); if (!error) error = source.move(target); } } else { // nothing besides the chunks.json and chunk folders should be here, // so ignore other files/content continue; } if (error) LOG_ERROR(error); }
Error createProject(const json::JsonRpcRequest& request, json::JsonRpcResponse* pResponse) { // read params std::string projectFile; json::Value newPackageJson, newShinyAppJson; Error error = json::readParams(request.params, &projectFile, &newPackageJson, &newShinyAppJson); if (error) return error; FilePath projectFilePath = module_context::resolveAliasedPath(projectFile); // package project if (!newPackageJson.is_null()) { // build list of code files bool usingRcpp; json::Array codeFilesJson; Error error = json::readObject(newPackageJson.get_obj(), "using_rcpp", &usingRcpp, "code_files", &codeFilesJson); if (error) return error; std::vector<FilePath> codeFiles; BOOST_FOREACH(const json::Value codeFile, codeFilesJson) { if (!json::isType<std::string>(codeFile)) { BOOST_ASSERT(false); continue; } FilePath codeFilePath = module_context::resolveAliasedPath(codeFile.get_str()); codeFiles.push_back(codeFilePath); } // error if the package dir already exists FilePath packageDir = projectFilePath.parent(); if (packageDir.exists()) return core::fileExistsError(ERROR_LOCATION); // create a temp dir (so we can import the list of code files) FilePath tempDir = module_context::tempFile("newpkg", "dir"); error = tempDir.ensureDirectory(); if (error) return error; // copy the code files into the tempDir and build up a // list of the filenames for passing to package.skeleton std::vector<std::string> rFileNames, cppFileNames; BOOST_FOREACH(const FilePath& codeFilePath, codeFiles) { FilePath targetPath = tempDir.complete(codeFilePath.filename()); Error error = codeFilePath.copy(targetPath); if (error) return error; std::string ext = targetPath.extensionLowerCase(); std::string file = string_utils::utf8ToSystem(targetPath.filename()); if (boost::algorithm::starts_with(ext,".c")) cppFileNames.push_back(file); else rFileNames.push_back(file); }
Error createProject(const json::JsonRpcRequest& request, json::JsonRpcResponse* pResponse) { // read params std::string projectFile; json::Value newPackageJson; json::Value newShinyAppJson; Error error = json::readParams(request.params, &projectFile, &newPackageJson, &newShinyAppJson); if (error) return error; FilePath projectFilePath = module_context::resolveAliasedPath(projectFile); if (!newShinyAppJson.is_null()) { // error if the shiny app dir already exists FilePath appDir = projectFilePath.parent(); if (appDir.exists()) return core::fileExistsError(ERROR_LOCATION); // now create it Error error = appDir.ensureDirectory(); if (error) return error; // copy ui.R and server.R into the project const char * const kUI = "ui.R"; const char * const kServer = "server.R"; std::string shinyVer; if (module_context::isPackageVersionInstalled("shiny", "0.9")) shinyVer = "shiny-0.9"; else shinyVer = "shiny"; FilePath shinyDir = session::options().rResourcesPath().childPath( "templates/" + shinyVer); error = shinyDir.childPath(kUI).copy(appDir.childPath(kUI)); if (error) LOG_ERROR(error); error = shinyDir.childPath(kServer).copy(appDir.childPath(kServer)); if (error) LOG_ERROR(error); // add first run actions for the source files addFirstRunDoc(projectFilePath, kUI); addFirstRunDoc(projectFilePath, kServer); // create the project file return r_util::writeProjectFile(projectFilePath, ProjectContext::buildDefaults(), ProjectContext::defaultConfig()); } // default project else { // create the project directory if necessary error = projectFilePath.parent().ensureDirectory(); if (error) return error; // create the project file if (!projectFilePath.exists()) { return r_util::writeProjectFile(projectFilePath, ProjectContext::buildDefaults(), ProjectContext::defaultConfig()); } else { return Success(); } } }
Error createProject(const json::JsonRpcRequest& request, json::JsonRpcResponse* pResponse) { // read params std::string projectFile; json::Value newPackageJson; Error error = json::readParams(request.params, &projectFile, &newPackageJson); if (error) return error; FilePath projectFilePath = module_context::resolveAliasedPath(projectFile); // default project if (newPackageJson.is_null()) { // create the project directory if necessary error = projectFilePath.parent().ensureDirectory(); if (error) return error; // create the project file if (!projectFilePath.exists()) { return r_util::writeProjectFile(projectFilePath, ProjectContext::defaultConfig()); } else { return Success(); } } // package project else { // build list of code files bool usingRcpp; json::Array codeFilesJson; Error error = json::readObject(newPackageJson.get_obj(), "using_rcpp", &usingRcpp, "code_files", &codeFilesJson); if (error) return error; std::vector<FilePath> codeFiles; BOOST_FOREACH(const json::Value codeFile, codeFilesJson) { if (!json::isType<std::string>(codeFile)) { BOOST_ASSERT(false); continue; } FilePath codeFilePath = module_context::resolveAliasedPath(codeFile.get_str()); codeFiles.push_back(codeFilePath); } // error if the package dir already exists FilePath packageDir = projectFilePath.parent(); if (packageDir.exists()) return core::fileExistsError(ERROR_LOCATION); // create a temp dir (so we can import the list of code files) FilePath tempDir = module_context::tempFile("newpkg", "dir"); error = tempDir.ensureDirectory(); if (error) return error; // copy the code files into the tempDir and build up a // list of the filenames for passing to package.skeleton std::vector<std::string> rFileNames, cppFileNames; BOOST_FOREACH(const FilePath& codeFilePath, codeFiles) { FilePath targetPath = tempDir.complete(codeFilePath.filename()); Error error = codeFilePath.copy(targetPath); if (error) return error; std::string ext = targetPath.extensionLowerCase(); std::string file = string_utils::utf8ToSystem(targetPath.filename()); if (boost::algorithm::starts_with(ext,".c")) cppFileNames.push_back(file); else rFileNames.push_back(file); } // if the list of code files is empty then add an empty file // with the same name as the package (but don't do this for // Rcpp since it generates a hello world file) if (codeFiles.empty() && !usingRcpp) { std::string srcFileName = packageDir.filename() + ".R"; FilePath srcFilePath = tempDir.complete(srcFileName); Error error = core::writeStringToFile(srcFilePath, ""); if (error) return error; rFileNames.push_back(string_utils::utf8ToSystem(srcFileName)); } // temporarily switch to the tempDir for package creation RestoreCurrentPathScope pathScope(module_context::safeCurrentPath()); tempDir.makeCurrentPath(); // call package.skeleton r::exec::RFunction pkgSkeleton(usingRcpp ? "Rcpp:::Rcpp.package.skeleton" : "utils:::package.skeleton"); pkgSkeleton.addParam("name", string_utils::utf8ToSystem(packageDir.filename())); pkgSkeleton.addParam("path", string_utils::utf8ToSystem(packageDir.parent().absolutePath())); pkgSkeleton.addParam("code_files", rFileNames); if (usingRcpp && module_context::haveRcppAttributes()) { if (!cppFileNames.empty()) { pkgSkeleton.addParam("example_code", false); pkgSkeleton.addParam("cpp_files", cppFileNames); } else { pkgSkeleton.addParam("attributes", true); } } error = pkgSkeleton.call(); if (error) return error; // create the project file (allow auto-detection of the package // to setup the package build type & default options) r_util::RProjectConfig projConfig = ProjectContext::defaultConfig(); return r_util::writeProjectFile(projectFilePath, projConfig); }