1 /*
2  * HunspellCustomDictionaries.cpp
3  *
4  * Copyright (C) 2021 by RStudio, PBC
5  *
6  * Unless you have received this program directly from RStudio pursuant
7  * to the terms of a commercial license agreement with RStudio, then
8  * this program is licensed to you under the terms of version 3 of the
9  * GNU Affero General Public License. This program is distributed WITHOUT
10  * ANY EXPRESS OR IMPLIED WARRANTY, INCLUDING THOSE OF NON-INFRINGEMENT,
11  * MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE. Please refer to the
12  * AGPL (http://www.gnu.org/licenses/agpl-3.0.txt) for more details.
13  *
14  */
15 
16 #include <core/spelling/HunspellCustomDictionaries.hpp>
17 
18 #include <boost/bind/bind.hpp>
19 
20 #include <core/Algorithm.hpp>
21 #include <core/Log.hpp>
22 
23 using namespace boost::placeholders;
24 
25 namespace rstudio {
26 namespace core {
27 namespace spelling {
28 
dictionaries() const29 std::vector<std::string> HunspellCustomDictionaries::dictionaries() const
30 {
31    std::vector<std::string> dictionaries;
32    Error error = customDictionariesDir_.ensureDirectory();
33    if (error)
34    {
35       LOG_ERROR(error);
36       return dictionaries;
37    }
38 
39    std::vector<FilePath> children;
40    error = customDictionariesDir_.getChildren(children);
41    if (error)
42    {
43       LOG_ERROR(error);
44       return dictionaries;
45    }
46 
47    algorithm::copy_transformed_if(
48          children.begin(),
49          children.end(),
50          std::back_inserter(dictionaries),
51          boost::bind(&FilePath::hasExtensionLowerCase, _1, ".dic"),
52          boost::bind(&FilePath::getStem, _1));
53 
54    return dictionaries;
55 }
56 
dictionaryPath(const std::string & name) const57 FilePath HunspellCustomDictionaries::dictionaryPath(
58                                           const std::string& name) const
59 {
60    return customDictionariesDir_.completeChildPath(name + ".dic");
61 }
62 
add(const FilePath & dicPath) const63 Error HunspellCustomDictionaries::add(const FilePath& dicPath) const
64 {
65    // validate .dic extension
66    if (!dicPath.hasExtensionLowerCase(".dic"))
67    {
68       return systemError(boost::system::errc::invalid_argument,
69                          ERROR_LOCATION);
70    }
71 
72    // remove existing with same name
73    std::string name = dicPath.getStem();
74    Error error = remove(name);
75    if (error)
76       LOG_ERROR(error);
77 
78    // add it
79    return dicPath.copy(dictionaryPath(name));
80 }
81 
remove(const std::string & name) const82 Error HunspellCustomDictionaries::remove(const std::string& name) const
83 {
84    return dictionaryPath(name).removeIfExists();
85 }
86 
87 
88 } // namespace spelling
89 } // namespace core
90 } // namespace rstudio
91