1. Contexte
Dans les sites Web d'aujourd'hui, il existe de plus en plus de canaux d'accès et la technologie est de plus en plus avancée, comme WAP, SMS, EMAIL, Web traditionnel, Socket, etc. Si même les bases de données et LDAP sont incluses, l'accès Si ainsi, l'espace qui doit être élargi dans la conception doit être très bon pour garantir que lors de l'ajout de nouveaux canaux, aucune modification supplémentaire du code ou même des changements de code ne soient nécessaires. Mais est-ce possible ? Je ne pense pas que ce soit possible, mais existe-t-il un moyen de mieux résoudre la perfection de ce cadre d'accès multicanal
2. Architecture
?[Figure 1]
Comme le montre la figure 1, lorsque tous les accès existants ont été utilisés, les concepteurs sont éblouis. S'il s'agit de rassembler des personnes, alors ces programmes peuvent être écrits de n'importe quelle manière, et cela fonctionnera certainement. , mais ce sera plus pénible à maintenir. Revenons à la question : comment pouvons-nous obtenir une implémentation plus parfaite ?
[Figure 2]
La figure 2 ressemble à une pieuvre avec huit griffes. Les pattes de la pieuvre sont respectivement connectées à tous les canaux d'accès. Le noyau de la connexion de tous ces canaux est le XMLRouter, la tête de la pieuvre. Le rôle du routeur ici est de. communiquer avec tous les canaux et réaliser Les avantages du routage des données et de l'amélioration de l'évolutivité et de la flexibilité de l'architecture du système seront nombreux. Il est appelé XMLRouter car si XML, un langage flexible et standardisé, n'est pas utilisé comme support de transmission de données, la charge de travail du routeur augmentera également de façon exponentielle. La définition de la spécification XML entraînera une expansion future.
3. Idées et modèles
L'idée originale de XMLRouter est venue de la carte mère de l'ordinateur et <
>Dans le modèle Builder, l'emplacement PCI de la carte mère de l'ordinateur définit la spécification PCI. Tant que la carte que vous produisez répond à la norme PCI, elle peut fonctionner lorsque vous l'insérez dans la carte mère. Quant à son fonctionnement à l'intérieur, elle l'est. été packagé. Builder Pattern propose de séparer la construction complexe et de la mettre en œuvre étape par étape. XMLRouter sépare ces canaux complexes et les exécute un par un.
Afin de communiquer avec le routeur, une interface unifiée doit être définie lors de l'accès. le canal, ici il est appelé Services. Tant que le programme est conforme à la spécification Services, il peut accéder au routeur et aux données de routage.
Le mode Factory et le mode Composite
XMLRouter seront générés en utilisant le mode Factory dans la conception réelle. RouterFactory, il sera placé dans la file d'attente lors de sa mise en service. Les données de transmission, les données de réception et les données de retour sont toutes appelées depuis le routeur correspondant depuis la file d'attente, et le mode composite est appliqué.
4.
Fichier de configuration XML Fichier XML
.pour le routeur L'utilisation est divisée en deux parties La première est la configuration du routeur, telle que :
Voici une citation : <?xml version="1.0" ?> <services> <!-- Service de base de données --> <service name="database" type="database" class="com.web.service.DBService"> <connecteur driver="com.microsoft.jdbc.sqlserver.SQLServerDriver" url="jdbc:microsoft:sqlserver://192.168.0.179:1433" user="test" mot de passe="test" /> </service> <!--Service Web--> <service name="web" type="web" class="com.web.service.WebService" > <connecteur /> </service> … </services> |
Il s'agit du fichier de configuration du routeur. Le nœud de service représente le canal auquel il faut accéder. Le nœud de service contient le sous-nœud du connecteur. La configuration du sous-nœud se distingue par son type. une base de données, elle contient des attributs tels que l'url, l'utilisateur, le mot de passe, le pilote, etc., s'il s'agit d'un socket, elle contient des attributs tels que le port et le maxthread. Les valeurs d'attribut peuvent être configurées selon votre propre définition. .
Un autre type de fichier XML est le fichier de données de transaction XML, qui est utilisé pour transférer des données dans tous les services. Chaque service contient son propre fichier XML, tel que webtrans.xml, a le format suivant :
Voici une citation : <?xml version="1.0" ?> <transaction> <trans name="addDoc" service="database" method="insert"> <property name="createtime" type="timestamp"/> <property name="creatorid" type="long"/> <property name="doctypeid" type="int"/> <property name="docstatusid" type="int"/> </trans> </transaction> |
Le format dbtrans.xml correspondant est le suivant
Voici une citation : <trans name="addDoc" table="TDOC_DOCS" method="insert"> <primarykey name="docid" /> <ensemble> <property name="createtime" type="timestamp"/> <property name="creatorid" type="long"/> <property name="doctypeid" type="int"/> <property name="docstatusid" type="int"/> </ensemble> </trans> |
Le reste du XML peut être personnalisé selon ces règles
5. Implémentation technique
de RouterFactory.
Voici une citation : paquet com.web.router ; importer com.web.platform.Exception.RouterException ; import java.util.java/util/Hashtable.java.html" target="_blank">Hashtable ; |
Ce qui suit est un fragment de référence : /** * Classes générées et effacées par le routeur */ classe publique RouterFactory { /** * Façade d'arbre stockée par le routeur */ private static java/util/Hashtable.java.html" target="_blank">Hashtable QueuePairFront = null; /** * Arbre stocké par le routeur */ private static java/util/Hashtable.java.html" target="_blank">Hashtable QueuePairBack = null; /** * Arbre stocké par le routeur */ private static java/util/Hashtable.java.html" target="_blank">Hashtable QueueRouter = null; /** * XMLRouter renvoyé */ Instance XMLRouter statique publique = null ; /** *Définition du routeur */ public statique RouterDefine routerdefine = null; /** * Numéro d'identification du routeur */ public statique long routeIndex = 0 ; /** * @roseuid 3F169C21027C */ public RouterFactory() { } /** * Initialiser la table de hachage et le vecteur */ public static void initFactory() lève java/lang/Exception.java.html" target="_blank">Exception { QueuePairFront = new java/util/Hashtable.java.html" target="_blank">Hashtable(); QueuePairBack = new java/util/Hashtable.java.html" target="_blank">Hashtable(); QueueRouter = new java/util/Hashtable.java.html" target="_blank">Hashtable(); initRouteDefine(); } /** * Initialiser les paramètres d'itinéraire * */ private static void initRouteDefine() lève java/lang/Exception.java.html" target="_blank">Exception { si (routerdefine == null) routerdefine = nouveau RouterDefine(); routerdefine.loadRouterDef(); } /** * Instance de retour * @return com.web.router.XMLRouter */ public static XMLRouter getInstance (index long) lance une exception RouterException { return (XMLRouter)QueueRouter.get(new java/lang/Long.java.html" target="_blank">Long(index)); } /** * Générer une instance de XMLRouter * @return com.web.router.XMLRouter * @roseuid 3F1618A103BC */ public static XMLRouter popInstance() lève RouterException { routeIndex++; instance = nouveau XMLRouter(routeIndex); setDefine( instance ); QueueRouter.put(new java/lang/Long.java.html" target="_blank">Long(routeIndex), instance); instance de retour ; } /** * Effacer la table de hachage, le vecteur, etc. * @roseuid 3F1618B203C1 */ private static void freeResource() lève java/lang/Exception.java.html" target="_blank">Exception { QueuePairFront.clear(); QueuePairBack.clear(); QueueRouter.clear(); QueuePairFront = QueuePairBack = QueueRouter = null ; } /** * Effacer l'instance * @param instanceID * @throwsException */ public static void removeInstance (instance XMLRouter) génère une exception java/lang/Exception.java.html" target="_blank"> { instance.clear(); QueueRouter.remove( new java/lang/Long.java.html" target="_blank">Long(instance.getIndex() ) ) ; } /** * La méthode est Null. * @return booléen */ public statique booléen isNull() { … renvoie faux ; } } |
Voici une citation : paquet com.web.router ; importer com.web.platform.Exception.RouterException ; importer com.web.common.* ; importer java.util.* ; importer java.lang.reflect.java/lang/reflect/Method.java.html" target="_blank">Méthode ; importer java.lang.reflect.java/lang/reflect/Constructor.java.html" target="_blank">Constructeur ; /** * @auteur keli * @version 0.0.1 * La clé de la plateforme, la classe de routage, chaque routeur lira depuis RouterFactory * L'arborescence avant, arrière et routeIndex stockée par le routeur est destinée au routage * Les objets appliqués peuvent être effacés ultérieurement. * Le routeur peut implémenter des fonctions synchrones et asynchrones. */ Classe publique XMLRouter { /** * Façade d'arbre stockée par le routeur */ private static java/util/Hashtable.java.html" target="_blank">Hashtable QueuePairFront = null; /** * Arbre stocké par le routeur */ private static java/util/Hashtable.java.html" target="_blank">Hashtable QueuePairBack = null; /** * Le numéro d'index de ce routeur */ long itinéraireIndex privé = 0 ; /** * Paramètres du routeur */ privé RouterDefine définir = null ; /** * Utilisé pour déterminer le point de départ de l'itinéraire */ private java/lang/String.java.html" target="_blank">String action = ""; /** *Cette variable est uniquement utilisée pour postuler à une nouvelle classe dans la méthode routeto */ private java/lang/String.java.html" target="_blank">String nom de classe = ""; /** */ public XMLRouter (index long) { routeIndex = index; } /** * Routage * @throws Exception * @roseuid 3F1616BD0186 */ le routage public void (Env env) génère une exception RouterException, java/lang/Exception.java.html" target="_blank">Exception { /*Si c'est le point de départ*/ si ( action.equalsIgnoreCase ( RouterConstant.CFG_FUNC_ROUTETO ) ) { … } /*Si c'est un point de retour*/ sinon si( action.equalsIgnoreCase( RouterConstant.CFG_FUNC_ROUTEBACK ) ) { … } /*Sinon c'est une erreur*/ autre throw new RouterException("Erreur d'action du routeur."); } /** * Lisez le numéro d'identification de ce routeur. * @retour long */ public long getIndex() { retourner routeIndex ; } /** * Effacez tous les objets. * @throwsRouterException */ public void clear() lance RouterException { QueuePairFront.remove(new java/lang/Long.java.html" target="_blank">Long(routeIndex)); QueuePairBack.remove(new java/lang/Long.java.html" target="_blank">Long(routeIndex)); /*Recyclage du système*/ java/lang/System.java.html" target="_blank">System.runFinalization(); } /** * Définissez les paramètres de ce routeur. * @param déf * @throwsRouterException */ public void setDefine (RouterDefine def) lance une exception RouterException { définir = déf; } /** * Définir la valeur de l'action * @param actionName * @throwsRouterException */ public void setAction( java/lang/String.java.html" target="_blank">String actionName ) { action = nomaction ; } } |
Classe de services
Voici une citation : paquet com.web.common; importer com.web.platform.Exception.RouterException ; /** * La classe parent de Service, résumé */ classe abstraite publique RouteService { /** */ publicRouteService() { } /** * La méthode routeTo est le point de départ de la transaction. * @param env * @throwsRouterException */ public abstract void routeto (Env env) lève RouterException ; /** *routeBack, point final de la transaction, * @param env * @throwsRouterException */ public abstract void routeback (Env env) lève RouterException ; /** * La méthode routeaccept est le point de réception de la transaction et la fonction de réception de routeto. * routeaccept est la fonction de traitement principale des objets de transaction passifs * @param env * @throwsRouterException */ public abstract void routeaccept (Env env) lève RouterException ; /** * La méthode de routage est la fonction d'interface externe du Service * @throws RouterException */ public abstract void router() throws RouterException; |
Ensuite, vous devez implémenter toutes les classes de services, qui ne seront pas présentées ici.
6. Expliquez que
ce routeur ne peut jusqu'à présent implémenter que des transactions synchrones et ne prend pas en charge les transactions asynchrones pour le moment. Cependant, étant donné que le routeur est conçu à l'aide du modèle composite, la mise en œuvre de transactions asynchrones peut également être étendue, une analyse détaillée ne sera donc pas effectuée ici.