Пример #1
0
        /// <summary>
        /// Archive a file given the file contents.
        /// </summary>
        /// <param name="inputPath">The path of the file.</param>
        /// <param name="contents">The contents of the file.</param>
        public void Archive(PathTransformer.ITransformedPath inputPath, string contents)
        {
            if (string.IsNullOrEmpty(archive))
            {
                return;
            }

            ArchiveContents(inputPath, contents);
        }
Пример #2
0
        public static string TrapPath(ILogger logger, string?folder, PathTransformer.ITransformedPath path, TrapWriter.CompressionMode trapCompression)
        {
            var filename = $"{path.Value}.trap{TrapExtension(trapCompression)}";

            if (string.IsNullOrEmpty(folder))
            {
                folder = Directory.GetCurrentDirectory();
            }

            return(NestPaths(logger, folder, filename));
        }
Пример #3
0
        /// <summary>
        /// Finds the suitable directories for a given source file.
        /// Returns null if not included in the layout.
        /// </summary>
        /// <param name="sourceFile">The file to look up.</param>
        /// <returns>The relevant subproject, or null if not found.</returns>
        public SubProject?LookupProjectOrNull(PathTransformer.ITransformedPath sourceFile)
        {
            if (!useLayoutFile)
            {
                return(defaultProject);
            }

            return(blocks
                   .Where(block => block.Matches(sourceFile))
                   .Select(block => block.Directories)
                   .FirstOrDefault());
        }
Пример #4
0
        public TrapWriter(ILogger logger, PathTransformer.ITransformedPath outputfile, string?trap, string?archive, CompressionMode trapCompression, bool discardDuplicates)
        {
            this.logger          = logger;
            this.trapCompression = trapCompression;

            TrapFile = TrapPath(this.logger, trap, outputfile, trapCompression);

            writerLazy = new Lazy <StreamWriter>(() =>
            {
                var tempPath = trap ?? Path.GetTempPath();

                do
                {
                    /*
                     * Write the trap to a random filename in the trap folder.
                     * Since the trap path can be very long, we need to deal with the possibility of
                     * PathTooLongExceptions. So we use a short filename in the trap folder,
                     * then move it later.
                     *
                     * Although GetRandomFileName() is cryptographically secure,
                     * there's a tiny chance the file could already exists.
                     */
                    tmpFile = Path.Combine(tempPath, Path.GetRandomFileName());
                }while (File.Exists(tmpFile));

                var fileStream = new FileStream(tmpFile, FileMode.CreateNew, FileAccess.Write);

                Stream compressionStream;

                switch (trapCompression)
                {
                case CompressionMode.Brotli:
                    compressionStream = new BrotliStream(fileStream, CompressionLevel.Fastest);
                    break;

                case CompressionMode.Gzip:
                    compressionStream = new GZipStream(fileStream, CompressionLevel.Fastest);
                    break;

                case CompressionMode.None:
                    compressionStream = fileStream;
                    break;

                default:
                    throw new ArgumentOutOfRangeException(nameof(trapCompression), trapCompression, "Unsupported compression type");
                }


                return(new StreamWriter(compressionStream, utf8, 2000000));
            });
            this.archive           = archive;
            this.discardDuplicates = discardDuplicates;
        }
Пример #5
0
        private string tmpFile = "";     // The temporary file which is moved to trapFile once written.

        /// <summary>
        /// Adds the specified input file to the source archive. It may end up in either the normal or long path area
        /// of the source archive, depending on the length of its full path.
        /// </summary>
        /// <param name="originalPath">The path to the input file.</param>
        /// <param name="transformedPath">The transformed path to the input file.</param>
        /// <param name="inputEncoding">The encoding used by the input file.</param>
        public void Archive(string originalPath, PathTransformer.ITransformedPath transformedPath, Encoding inputEncoding)
        {
            if (string.IsNullOrEmpty(archive))
            {
                return;
            }

            // Calling GetFullPath makes this use the canonical capitalisation, if the file exists.
            var fullInputPath = Path.GetFullPath(originalPath);

            ArchivePath(fullInputPath, transformedPath, inputEncoding);
        }
Пример #6
0
        private void ArchiveContents(PathTransformer.ITransformedPath transformedPath, string contents)
        {
            var dest       = NestPaths(logger, archive, transformedPath.Value);
            var tmpSrcFile = Path.GetTempFileName();

            File.WriteAllText(tmpSrcFile, contents, utf8);
            try
            {
                FileUtils.MoveOrReplace(tmpSrcFile, dest);
            }
            catch (IOException ex)
            {
                // If this happened, it was probably because the same file was compiled multiple times.
                // In any case, this is not a fatal error.
                logger.Log(Severity.Warning, "Problem archiving " + dest + ": " + ex);
            }
        }
Пример #7
0
 public File(Context cx, string path) : base(cx)
 {
     this.OriginalPath = path;
     TransformedPath   = Context.Extractor.PathTransformer.Transform(OriginalPath);
 }
Пример #8
0
 /// <summary>
 /// Creates a folder entitiy with the given path.
 /// </summary>
 /// <param name="path">The path of the folder.</param>
 /// <returns>A folder entity.</returns>
 public Folder CreateFolder(PathTransformer.ITransformedPath path) => folders[path];
Пример #9
0
 public Folder(Context cx, PathTransformer.ITransformedPath path) : base(cx)
 {
     this.transformedPath = path;
 }
Пример #10
0
 /// <summary>
 /// Finds the suitable directories for a given source file.
 /// Returns the default project if not included in the layout.
 /// </summary>
 /// <param name="sourceFile">The file to look up.</param>
 /// <returns>The relevant subproject, or DefaultProject if not found.</returns>
 public SubProject LookupProjectOrDefault(PathTransformer.ITransformedPath sourceFile)
 {
     return(LookupProjectOrNull(sourceFile) ?? defaultProject);
 }
Пример #11
0
 /// <summary>
 /// Creates a trap writer for a given source/assembly file.
 /// </summary>
 /// <param name="srcFile">The source file.</param>
 /// <returns>A newly created TrapWriter.</returns>
 public TrapWriter CreateTrapWriter(ILogger logger, PathTransformer.ITransformedPath srcFile, TrapWriter.CompressionMode trapCompression, bool discardDuplicates) =>
 new TrapWriter(logger, srcFile, TRAP_FOLDER, SOURCE_ARCHIVE, trapCompression, discardDuplicates);
Пример #12
0
 /// <summary>
 /// Gets the name of the trap file for a given source/assembly file.
 /// </summary>
 /// <param name="srcFile">The source file.</param>
 /// <returns>The full filepath of the trap file.</returns>
 public string GetTrapPath(ILogger logger, PathTransformer.ITransformedPath srcFile, TrapWriter.CompressionMode trapCompression) =>
 TrapWriter.TrapPath(logger, TRAP_FOLDER, srcFile, trapCompression);
Пример #13
0
 public bool Matches(PathTransformer.ITransformedPath path) => FilePattern.Matches(filePatterns, path.Value, out var _);
Пример #14
0
 /// <summary>
 /// Is the source file included in the layout?
 /// </summary>
 /// <param name="path">The absolute path of the file to query.</param>
 /// <returns>True iff there is no layout file or the layout file specifies the file.</returns>
 public bool FileInLayout(PathTransformer.ITransformedPath path) => LookupProjectOrNull(path) != null;
Пример #15
0
        /// <summary>
        /// Attempts to archive the specified input file to the normal area of the source archive.
        /// The file's path must be sufficiently short so as to render the path of its copy in the
        /// source archive less than the system path limit of 260 characters.
        /// </summary>
        /// <param name="fullInputPath">The full path to the input file.</param>
        /// <param name="transformedPath">The transformed path to the input file.</param>
        /// <param name="inputEncoding">The encoding used by the input file.</param>
        /// <exception cref="PathTooLongException">If the output path in the source archive would
        /// exceed the system path limit of 260 characters.</exception>
        private void ArchivePath(string fullInputPath, PathTransformer.ITransformedPath transformedPath, Encoding inputEncoding)
        {
            var contents = File.ReadAllText(fullInputPath, inputEncoding);

            ArchiveContents(transformedPath, contents);
        }