private void Include(string args, ref Input input) { var match = IncludeRegex.Match(args); if (!match.Success) { throw new SqlCmdException("Invalid syntax in :r directive."); } string path; path = match.Groups[nameof(path)].Value; path = Unquote(path); path = ReplaceVariables(path); var text = IoHelper.ReadText(path); input = new Input(path, text, input); }
private static IReadOnlyList <string> ScanConfigFiles([NotNull] string entryFilePath, [NotNull] Encoding encoding) { var result = new List <string>(); var q = new Queue <(string Path, string BasePath)>(); entryFilePath = Path.GetFullPath(entryFilePath); q.Enqueue((Path: Path.GetFileName(entryFilePath), BasePath: Path.GetDirectoryName(entryFilePath))); while (q.Count > 0) { var(path, basePath) = q.Dequeue(); if (!Path.IsPathRooted(path)) { // Treat as absolute path. path = Path.Combine(basePath, path); } var globCharIndex = path.IndexOfAny(GlobHelper.PartialGlobChars); try { // The path has been expanded, e.g. xxx/**/*yyy.zzz -> C:\dir\xxx\**\*.yyy.zzz, // so a glob char should not appear be the first char. if (globCharIndex == 0) { throw new ApplicationException("Unexpected: glob char index == 0"); } if (globCharIndex > 0) { var sepIndex = path.LastIndexOfAny(GlobHelper.PathSeparatorChars, globCharIndex - 1); if (sepIndex < 0) { throw new ArgumentOutOfRangeException(nameof(sepIndex)); } basePath = path.Substring(0, sepIndex + 1); var dirInfo = new DirectoryInfo(basePath); if (dirInfo.Exists) { var subPath = path.Substring(sepIndex + 1); foreach (var fileInfo in dirInfo.GlobFiles(subPath)) { if (result.Contains(fileInfo.FullName)) { continue; } q.Enqueue((Path: fileInfo.Name, BasePath: fileInfo.DirectoryName)); } } else { GameLog.Warn("{0}: Config file {1}: Cannot find directory '{2}'.", ReflectionHelper.GetCallerName(), entryFilePath, dirInfo.FullName); } continue; } else { if (!result.Contains(path)) { result.Add(path); } } using (var fileStream = File.Open(path, FileMode.Open, FileAccess.Read, FileShare.Read)) { using (var streamReader = new StreamReader(fileStream, encoding)) { // Reads until the first line which: // - is not blank; // - does not start with "#", or // the content inside the comments does not start with "@include" while (!streamReader.EndOfStream) { var line = streamReader.ReadLine(); if (line == null) { break; } if (string.IsNullOrWhiteSpace(line)) { continue; } line = line.TrimStart(); if (!line.StartsWith("#")) { break; } line = line.Substring(1).Trim(); var match = IncludeRegex.Match(line); if (!match.Success) { break; } var includePath = match.Groups["path"].Value; if (string.IsNullOrEmpty(includePath)) { continue; } q.Enqueue((Path: includePath, BasePath: basePath)); } } } } catch (Exception) { GameLog.Error("An exception occurred while parsing config file '{0}'.", path); throw; } } return(result); }