示例#1
0
        private static T[] GetAll___ <T>(
            Assembly a, string discriminator,
            Func <IEnumerable <string>, IEnumerable <T> > decode,
            Func <IEnumerable <Type>, IEnumerable <T> > createResult,
            Func <T[], IEnumerable <string> > encode
            )
        {
            var assemblyFileName  = a.Location;
            var cacheFileName     = CreateCacheFileName(assemblyFileName, discriminator.ToGuid());
            var assemblyTimeStamp = File.GetLastWriteTimeUtc(assemblyFileName);

            if (File.Exists(cacheFileName))
            {
                /* var cacheFileTimeStamp = */ File.GetLastWriteTimeUtc(cacheFileName);
                var lines  = File.ReadAllLines(cacheFileName);
                var header = lines.Length > 0 ? CacheFileHeader.Parse(lines[0]) : null;
                if (header != null && header.TimeStampOfCachedFile == assemblyTimeStamp)
                {
                    // return cached types
                    Report.Line(4, "[cache hit ] {0}", a);
                    return(decode(lines.Skip(1)).ToArray());
                }
            }

            Report.Line(4, "[cache miss] {0}", a);

            // Notes by hs:
            // previously (rev 19495) typeloadexception resulted in empty result set.
            // even in case of typeloadexception there may be some successfully loaded
            // types in result set. Just continue processing with these types
            // effect: dlls with external unused dependencies don't have to be shipped.
            Type[] ts = new Type[0];
            try
            {
                ts = a.GetTypes().ToArray();
            }
            catch (ReflectionTypeLoadException e)
            {
                Report.Begin("ReflectionTypeLoadException error in assembly {0}", a.GetName().Name);
                Report.Line("Full assembly name is {0}.", a.FullName);
                Report.Line("Exception is {0}", e);
                Report.Begin("Loader exceptions are");
                foreach (var x in e.LoaderExceptions)
                {
                    Report.Line("{0}", x);
                }
                Report.End();
                Report.End();
                ts = e.Types.Where(t => t != null).ToArray();
            }

            var result = createResult(ts).ToArray();

            // write cache file
            var headerLine =
                new CacheFileHeader {
                Version = 1, TimeStampOfCachedFile = assemblyTimeStamp
            }
            .ToString()
            .IntoIEnumerable()
            ;

            File.WriteAllLines(cacheFileName, headerLine.Concat(encode(result)).ToArray());

            return(result);
        }