| 
									
										
										
										
											2017-01-04 03:08:15 +08:00
										 |  |  | module.exports = function PluginEnvironment() { | 
					
						
							| 
									
										
										
										
											2025-04-22 20:42:33 +08:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * @type {{ name: string, handler: EXPECTED_FUNCTION }[]} | 
					
						
							|  |  |  | 	 */ | 
					
						
							| 
									
										
										
										
											2017-12-06 22:12:37 +08:00
										 |  |  | 	const events = []; | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2025-04-22 20:42:33 +08:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * @param {string} name the name | 
					
						
							|  |  |  | 	 * @param {EXPECTED_FUNCTION} handler the handler | 
					
						
							|  |  |  | 	 */ | 
					
						
							| 
									
										
										
										
											2017-12-06 22:12:37 +08:00
										 |  |  | 	function addEvent(name, handler) { | 
					
						
							|  |  |  | 		events.push({ | 
					
						
							|  |  |  | 			name, | 
					
						
							|  |  |  | 			handler | 
					
						
							|  |  |  | 		}); | 
					
						
							|  |  |  | 	} | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2025-04-22 20:42:33 +08:00
										 |  |  | 	/** | 
					
						
							|  |  |  | 	 * @param {string} hookName a hook name | 
					
						
							|  |  |  | 	 * @returns {string} an event name | 
					
						
							|  |  |  | 	 */ | 
					
						
							| 
									
										
										
										
											2017-12-06 22:12:37 +08:00
										 |  |  | 	function getEventName(hookName) { | 
					
						
							|  |  |  | 		// Convert a hook name to an event name.
 | 
					
						
							|  |  |  | 		// e.g. `buildModule` -> `build-module`
 | 
					
						
							| 
									
										
										
										
											2024-07-31 10:39:30 +08:00
										 |  |  | 		return hookName.replace(/[A-Z]/g, c => `-${c.toLowerCase()}`); | 
					
						
							| 
									
										
										
										
											2017-12-06 22:12:37 +08:00
										 |  |  | 	} | 
					
						
							| 
									
										
										
										
											2017-01-04 03:08:15 +08:00
										 |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-03-29 06:10:15 +08:00
										 |  |  | 	this.getEnvironmentStub = function () { | 
					
						
							| 
									
										
										
										
											2017-12-06 22:12:37 +08:00
										 |  |  | 		const hooks = new Map(); | 
					
						
							| 
									
										
										
										
											2017-01-04 03:08:15 +08:00
										 |  |  | 		return { | 
					
						
							| 
									
										
										
										
											2017-12-06 22:12:37 +08:00
										 |  |  | 			plugin: addEvent, | 
					
						
							|  |  |  | 			// TODO: Figure out a better way of doing this
 | 
					
						
							|  |  |  | 			// In the meanwhile, `hooks` is a `Proxy` which creates fake hooks
 | 
					
						
							|  |  |  | 			// on demand. Instead of creating a dummy object with a few `Hook`
 | 
					
						
							|  |  |  | 			// method, a custom `Hook` class could be used.
 | 
					
						
							| 
									
										
										
										
											2019-08-22 19:26:45 +08:00
										 |  |  | 			hooks: new Proxy( | 
					
						
							|  |  |  | 				{}, | 
					
						
							|  |  |  | 				{ | 
					
						
							|  |  |  | 					get(target, hookName) { | 
					
						
							|  |  |  | 						let hook = hooks.get(hookName); | 
					
						
							|  |  |  | 						if (hook === undefined) { | 
					
						
							|  |  |  | 							const eventName = getEventName(hookName); | 
					
						
							|  |  |  | 							hook = { | 
					
						
							|  |  |  | 								tap(_, handler) { | 
					
						
							|  |  |  | 									addEvent(eventName, handler); | 
					
						
							|  |  |  | 								}, | 
					
						
							|  |  |  | 								tapAsync(_, handler) { | 
					
						
							|  |  |  | 									addEvent(eventName, handler); | 
					
						
							|  |  |  | 								}, | 
					
						
							|  |  |  | 								tapPromise(_, handler) { | 
					
						
							|  |  |  | 									addEvent(eventName, handler); | 
					
						
							|  |  |  | 								} | 
					
						
							|  |  |  | 							}; | 
					
						
							|  |  |  | 							hooks.set(hookName, hook); | 
					
						
							|  |  |  | 						} | 
					
						
							|  |  |  | 						return hook; | 
					
						
							| 
									
										
										
										
											2017-12-06 22:12:37 +08:00
										 |  |  | 					} | 
					
						
							|  |  |  | 				} | 
					
						
							| 
									
										
										
										
											2019-08-22 19:26:45 +08:00
										 |  |  | 			) | 
					
						
							| 
									
										
										
										
											2017-01-04 03:08:15 +08:00
										 |  |  | 		}; | 
					
						
							|  |  |  | 	}; | 
					
						
							|  |  |  | 
 | 
					
						
							| 
									
										
										
										
											2020-03-29 06:10:15 +08:00
										 |  |  | 	this.getEventBindings = function () { | 
					
						
							| 
									
										
										
										
											2017-01-04 03:08:15 +08:00
										 |  |  | 		return events; | 
					
						
							|  |  |  | 	}; | 
					
						
							|  |  |  | }; |