Repository: rollup/rollup
File: src/Module.ts (TypeScript)

Code before:
		this.info = {
			assertions,
			ast: null,
			code: null,
			get dynamicallyImportedIdResolutions() {
				return dynamicImports
					.map(({ argument }) => typeof argument === 'string' && module.resolvedIds[argument])
					.filter(Boolean) as ResolvedId[];
			},
			get dynamicallyImportedIds() {
				// We cannot use this.dynamicDependencies because this is needed before
				// dynamicDependencies are populated
				return dynamicImports.map(({ id }) => id).filter((id): id is string => id != null);
			},
			get dynamicImporters() {
				return dynamicImporters.sort();
			},
			get exportedBindings() {
				const reexportBindings = [...reexportDescriptions.entries()].reduce<
					Record<string, string[]>
				>((previous, currentValue) => {
					const [name, { source }] = currentValue;
					previous[source] ??= [];
					previous[source].push(name);
					return previous;
				}, {});
				const exportAllSourceBindings = [...exportAllSources].reduce<Record<string, ['*']>>(
					(previous, currentValue) => {
						previous[currentValue] = ['*'];
						return previous;
					},
					{}
				);
				const exportBindings: Record<string, string[]> =
					exports.size > 0 ? { '.': [...exports.keys()] } : {};
				return { ...exportBindings, ...reexportBindings, ...exportAllSourceBindings };
			},
			get exports() {
				return [
					...exports.keys(),
					...reexportDescriptions.keys(),
					...[...exportAllSources].map(() => '*')
				];
			},
			get hasDefaultExport() {
				// This information is only valid after parsing
				if (!module.ast) {
					return null;
				}
				return module.exports.has('default') || reexportDescriptions.has('default');
			},

Review comment (performance):
`reduce` has a tendency to be hard to read, and also may have sub-optimal performance as compared to a for-of loop. Why not just something like this

```suggestion
        const reexportBindings: Record<string, string[]> = {};
        for (const [name, { source }] of reexportDescriptions.entries()) {
          reexportBindings[source] ??= [];
          reexportBindings[source].push(name);
        }
```

Code after:
		this.info = {
			assertions,
			ast: null,
			code: null,
			get dynamicallyImportedIdResolutions() {
				return dynamicImports
					.map(({ argument }) => typeof argument === 'string' && module.resolvedIds[argument])
					.filter(Boolean) as ResolvedId[];
			},
			get dynamicallyImportedIds() {
				// We cannot use this.dynamicDependencies because this is needed before
				// dynamicDependencies are populated
				return dynamicImports.map(({ id }) => id).filter((id): id is string => id != null);
			},
			get dynamicImporters() {
				return dynamicImporters.sort();
			},
			get exportedBindings() {
				const exportBindings: Record<string, string[]> = { '.': [...exports.keys()] };

				for (const [name, { source }] of reexportDescriptions) {
					(exportBindings[source] ??= []).push(name);
				}

				for (const source of exportAllSources) {
					(exportBindings[source] ??= []).push('*');
				}

				return exportBindings;
			},
			get exports() {
				return [
					...exports.keys(),
					...reexportDescriptions.keys(),
					...[...exportAllSources].map(() => '*')
				];
			},
			get hasDefaultExport() {
				// This information is only valid after parsing
				if (!module.ast) {
					return null;
				}
				return module.exports.has('default') || reexportDescriptions.has('default');
			},
			get hasModuleSideEffects() {
				warnDeprecation(
					'Accessing ModuleInfo.hasModuleSideEffects from plugins is deprecated. Please use ModuleInfo.moduleSideEffects instead.',
					true,
					options
				);
				return this.moduleSideEffects;