| 82 | |
| 83 | |
| 84 | Try<ContainerPath> parseContainerPath(const string& rootDir, const string& dir) |
| 85 | { |
| 86 | // TODO(chhsiao): Consider using `<regex>`, which requires GCC 4.9+. |
| 87 | |
| 88 | // Make sure there's a separator at the end of the `rootDir` so that |
| 89 | // we don't accidentally slice off part of a directory. |
| 90 | const string prefix = path::join(rootDir, ""); |
| 91 | |
| 92 | if (!strings::startsWith(dir, prefix)) { |
| 93 | return Error( |
| 94 | "Directory '" + dir + "' does not fall under the root directory '" + |
| 95 | rootDir + "'"); |
| 96 | } |
| 97 | |
| 98 | vector<string> tokens = strings::tokenize( |
| 99 | dir.substr(prefix.size()), |
| 100 | stringify(os::PATH_SEPARATOR)); |
| 101 | |
| 102 | // A complete container path consists of 4 tokens: |
| 103 | // <type>/<name>/containers/<volume_id> |
| 104 | if (tokens.size() != 4 || tokens[2] != CONTAINERS_DIR) { |
| 105 | return Error( |
| 106 | "Path '" + path::join(tokens) + "' does not match the structure of a " |
| 107 | "container path"); |
| 108 | } |
| 109 | |
| 110 | ContainerPath path; |
| 111 | path.type = tokens[0]; |
| 112 | path.name = tokens[1]; |
| 113 | path.containerId.set_value(tokens[3]); |
| 114 | |
| 115 | return path; |
| 116 | } |
| 117 | |
| 118 | |
| 119 | string getContainerInfoPath( |