Skip to content

Commit

Permalink
added route listener
Browse files Browse the repository at this point in the history
  • Loading branch information
yousuf64 committed Sep 2, 2024
1 parent ba0e834 commit b74f5d2
Show file tree
Hide file tree
Showing 3 changed files with 55 additions and 13 deletions.
11 changes: 7 additions & 4 deletions packages/@productled/core/src/Productled.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import Plugin from './Plugin';
import ConfigStore from './ConfigStore';
import PluginStore from './PluginStore';
import DocumentService from './DocumentService';
import { RouteListener } from "./RouteListener";

type pluginName = string;

Expand All @@ -18,6 +19,7 @@ class Productled {
protected configStore: ConfigStore;
protected pluginStore: PluginStore;
protected documentService: DocumentService;
protected routeListener: RouteListener;

/**
* The constructor is private to ensure that the class is a singleton.
Expand All @@ -28,6 +30,7 @@ class Productled {
this.pluginStore = new PluginStore();
this.documentService = new DocumentService();
this.configStore = new ConfigStore();
this.routeListener = new RouteListener();
}

/**
Expand All @@ -52,12 +55,11 @@ class Productled {
/**
* This method is called when the route changes.
* It retrieves the hooks for the current route and executes them.
* @param {string} url - The URL of the new route
* @returns {Promise<void>}
*/
public routeChanged() {

const currentRoute = window.location.pathname;
const hooks = this.hookStore.getHooks(currentRoute);
public routeChanged(url: string) {
const hooks = this.hookStore.getHooks(url);

const hookExecuter = new HookExecuter(this.pluginStore, this.documentService);
hookExecuter.executeHooks(hooks);
Expand All @@ -76,6 +78,7 @@ class Productled {
// Get the hooks for the plugin and add them to the hook store
const hooks = this.configStore.getHooks(pluginName);
this.hookStore.addHooks(hooks, pluginName);
this.routeListener.addListener(this.routeChanged.bind(this));
}

}
Expand Down
47 changes: 47 additions & 0 deletions packages/@productled/core/src/RouteListener.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,47 @@
type RouteListenerFunc = (url: string) => void;

class RouteListener {
private listening: boolean = false;
private listeners: Array<RouteListenerFunc> = [];

addListener(listener: RouteListenerFunc): void {
this.listeners.push(listener);

if (!this.listening) {
this.listening = true;
this.startListen();

setTimeout(() => this.notifyListeners(window.location.pathname)) // Initial notification
}
}

private startListen() {
// Overriding the pushState method to notify listeners
const pushState = window.history.pushState;
window.history.pushState = (...args): void => {
pushState.apply(window.history, args);

const url = args[2];
if (!url) {
return;
} else if (url instanceof URL) {
this.notifyListeners(url.toString());
} else {
this.notifyListeners(url);
}
};
}

private notifyListeners(url: string): void {
for (const listener of this.listeners) {
// Scheduled for the next event loop
setTimeout(() => listener(url));
}
}

removeListener(listener: Function): void {
this.listeners = this.listeners.filter(l => l !== listener);
}
}

export { RouteListener, RouteListenerFunc };
10 changes: 1 addition & 9 deletions packages/samples/react-sample/src/ProductledInit.tsx
Original file line number Diff line number Diff line change
@@ -1,14 +1,6 @@
import React, { useEffect } from 'react';
import { useLocation } from 'react-router-dom';
import { Productled } from '@productled/core';
import React from 'react';

const ProductledInit: React.FC = () => {
const location = useLocation();

useEffect(() => {
Productled.getInstance().routeChanged();
}, [location.pathname]);

return null;
}

Expand Down

0 comments on commit b74f5d2

Please sign in to comment.