| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
Welcome to the Fido-History-Project 3rd Generation ! ![]()
IntroProject Team Members:
Project Development starts: ... some years ago (2004?, 2005?, 2006?) around Pfingsten Data Source: based on main rescans from Olav, Knut and Dirk (and some others), all *.pkt Program Souce: Actual Source is a bundle of PERL scripts. Port to PHP is probably possible FidoBase actual State (1.10.2009): ![]() The actual state is:
The actual system uses the Dual Write method. Pro's: its easy to implement Con's: if one node hangs, the replications hangs Better: Using an async multiple nodes replication mode Database Structure
CREATE TABLE `echo_0` ( `id` int(11) NOT NULL auto_increment, `ftscdate` varchar(20) NOT NULL default '', `datetime` timestamp NOT NULL default CURRENT_TIMESTAMP on update CURRENT_TIMESTAMP, `folder` varchar(72) NOT NULL default '', `fromnode` varchar(72) NOT NULL default '', `tonode` varchar(72) NOT NULL default '', `fromname` varchar(36) NOT NULL default '', `toname` varchar(36) NOT NULL default '', `subject` varchar(72) NOT NULL default '', `attrib` smallint(5) unsigned NOT NULL default '0', `msgid` varchar(72) NOT NULL default '', `replyid` varchar(72) NOT NULL default '', `origin` varchar(72) NOT NULL default '', `path` varchar(255) NOT NULL default '', `local` char(1) NOT NULL default 'Y', `rcvd` char(1) NOT NULL default 'N', `sent` char(1) NOT NULL default 'N', `kludges` mediumblob, `body` mediumblob, `seenby` mediumblob, `datewritten` datetime default NULL, `Uplink` int(10) unsigned default '0', PRIMARY KEY (`id`), UNIQUE KEY `dupecheck` (`folder`,`ftscdate`,`msgid`,`subject`), KEY `Export` (`datetime`,`folder`) ) ENGINE=MyISAM DEFAULT CHARSET=latin1; ToDo / Wishlist
Each downlink can connect to all cluster nodes. The connection will be a ftn mailer session. The session password is read from the online database that resides on each nodes cluster site. Mailbundles will be streamed online, on the fly to the connected downlink from the nodes cluster database (echo_temp). If the downlink connects a 2nd time onto anothers cluster node, the tables needs updated just in time, so the downlink doesn't receive the mailbundle again. So the actual system needs two more tables:
Normalized
Database Sync Methods
Database Sync Methods - Dual Writes![]() x1) Dual Writes This method is actual used by the FidoBase project (see above). Database Sync Methods - Coordinated CommitsDiscussionUsing Queues ?
![]() Queued Writes Queue-IN: needs information of source (FTN Mailer or Cluster Node Update).
Push or Pull Updates or Both ?Push Update
Push and/or Pull or Both updates needs info about available cluster nodes. ... so the list of cluster nodes can increase / decrease and is flexible. If a cluster node goes offline forever, all related records in the Queue-OUT can be deleted. Problem solved. Records needs to be created in the Queue-OUT for all cluster nodes except the own cluster-node. List of ProcessesProcess 1 - FTN mailer connection
Process 2 - Update Process
Process 3 - Maintenance Process If a cluster node goes offline forever, the queues still needs cleaned from records for this offline cluster node. Full and/or partial Rescans(between cluster nodes)Full or partial rescans are no problem with this design. Trigger a full rescan exports all records from the database to the Queue-OUT for a specific cluster node. Partial rescans can be handled by count or days (export the last 5000 records, export the last 3 months). As of the dupe detection on the other side, dupe records are prevented. Downlinks Handling ?This procedure describes only the sync of cluster nodes with updates from FTN mailers. But it doesn't includes the update to the downlinks. How get the downlinks their bundles?
i. has the problem, that each cluster node has to queue all the mails for all downlinks, so the mails in the Queue-OUT needs to be duplicated to all real cluster nodes, because each downlink can connect to one of the other real cluster nodes. If the downlink connects to one real cluster node, the pulled mails from Queue-OUT also needs deleted from the Queue-OUT of the other real cluster nodes too. ii. the order of mails in each cluster nodes database can vary as the input may be unordered. This complicates the use of highwater marks. The highwater mark in database of cluster node A isn't the same highwater mark in the 2nd database of cluster node B and vice versa. If a downlink connects to a cluster node, the cluster node has to identify the point of which mails the downlink has received the last mail in one area (this is the same problem for all connected areas). ![]() Downlink 1 connects to Cluster Node A, transfers some mails Downlink 2 connects to Cluster Node B, transfers some mails ![]() Mails from Downlink 1 still gets replicated from Cluster Node A to Cluster Node B ![]() and Mails from Downlink 2 still gets replicated from Cluster Node B to Cluster Node A ![]() All tables are synchronized What's next time Downlink 2 connects to Cluster Node A and tries to get his 'actual' mails ? Remember: Downlink 2 sends mails Echo 1: #6, Echo 2: #4, #5, #6. The last sent mails for Echo #1 is #3, and for Echo 2 is #2. So sending all mails after Echo 1 #3 and Echo 2 #2 doesn't fit. Downlink 2 only needs the blue ones. Using addtl. Temp table? ![]() Filling Temp Downlinks table The next time, Downlink 2 connects to Cluster Node A, Cluster Node A sends mail beginning after row E2:2 => E1:4, E1:5, E2:3, skipping: E1:6, E2:4, E2:5, E2:6 and sets Highwate mark to row E2:6 ![]() Temp table updated at Cluster Node A for Downlink 2 Replicate information to Cluster Node B: DL2: E1:4+, E1:5+, E2:3+ ![]() Temp table on Cluster Node B now receiving update information from Cluster Node A ![]() Temp table updated on Cluster Node B ![]() New state Temp table on Cluster Node B Flat table structure for Temp Downlinks table [-----------Mails-----------] [DL1,DL2,...,DLn] Table (?), Folder (?), MailID, DownlinkID, State Replication Agent Procedure:
for i = 1 to n-Updates
for j = 1 to n-Downlinks
Dest = Downlinks[j]
if Dest != MyNodeID
case Action==AddMail
Queue-OUT(From:MyNodeID,To:Dest,Action:AddMail,Content:add(id,ftscdate,datetime,folder,...))
case Action==UpdateTemp
Queue-OUT(From:MyNodeID,To:Dest,Action:UpdateTemp,Content:update(MailID,DL#,state))
endif
next
next
Requirements
Further ActionsAdd, Remove Cluster NodesTo add and remove Cluster Nodes, a table that holds the Cluster Nodes info needs to exist. Update Record thru Replication process. Proposed table structure Cluster Nodes: ClusterNodesID, AKA, Name Add, Remove Downlinks To add and remove Downlinks, a table for Downlinks (with Session Password) needs to exist. Update record thru Replication process. Proposed table structure Cluster Nodes: DownlinkID, AKA, Name, SessionPwd Update Table Structures ? To add and remove Table Columns (Structureupdate) a procedure needs to exist Update table structures thru Replication process ? Updated Replication Agent Procedure:
for i = 1 to n-Updates
for j = 1 to n-ClusterNodes
Dest = ClusterNodes[j]
if Dest != MyNodeID
case Action==AddMail
Queue-OUT(From:MyNodeID,To:Dest,Action:AddMail,Content:add(id,ftscdate,datetime,folder,...))
case Action==UpdateTemp
Queue-OUT(From:MyNodeID,To:Dest,Action:UpdateTemp,Content:update(MailID,DL#,state))
case Action==AddClusterNode
Queue-OUT(From:MyNodeID,To:Dest,Action:AddClusterNode,Content:add(ClusterNodeID,AKA,Name))
case Action==AddDownlink
Queue-OUT(From:MyNodeID,To:Dest,Action:AddDownlink,Content:add(DownlinkID,AKA,Name,SessionPwd))
case Action==DelClusterNode
Queue-OUT(From:MyNodeID,To:Dest,Action:DelClusterNode,Content:del(ClusterNodeID))
case Action==DelDownlink
Queue-OUT(From:MyNodeID,To:Dest,Action:DelDownlink,Content:del(DownlinkID))
endif
next
next
Exports, External Links and Dupe Ring detectionsCase: Two links connected to one of the cluster nodes (aka BBR0) One link sends new mail (FTN mailer goes to Queue-IN) MsgID#1 created at cluster node A Another link sends the same mail to another cluster node (FTN mailer) MsgID#2 created on cluster node B Now dupe collision detection needs to compare MsgID #1 and #2 Which MsgID will win ? Using the cluster node table ascending order of hirarchy can be used to for select the higher priority for one of these mails If one cluster node goes offline, the next one is the virtual master for the moment of dupe collision If the failed cluster node comes back online, the authoritive restore overwrites dupe collisions upto the moment the cluster node is in sync again. Next problem: One link rcvd mail from downlink 1, downlink sends also mail thru FTN channel to downlink 2 (but needs some time). Cluster node forwards and exports mail to downlink 2. Now dupe detection is at FTN channel side, unreachable for the cluster node dupe detection process. Prevent sending mails to downlinks with known addtl. FTN links ? Implement a path analyse ? (aka CPD circular path detection) ![]() Dupe Detection with external links The collision detection process: 1. rcvd dupe msg 2. is one of the msgs from (last) dupe-master? 3. if yes, replace Id with Id from dupe-master 4. if no, is (last) master online? 5. send msgs request to master 6. dupe-master sends replace Id with dupe-master-Id for msg# 7. if dupe-master isn't online, the next one in the cluster nodes table becomes dupe-master The problem: FTN mailer downlinks doesn't have their own intelligence but needs to be included into the sync schema. One possible solution can be to build up the replication schema for FTN mailer downlinks within the database virtualy. This needs inclusion for all connected and sub-connected FTN mailer systems that are connected to any of the echo areas. If mails are exported to FTN mailer downlink #1 who has 2 FTN mailer downlinks the export has to be recorded into the system too. Cluster node A exports to FTN mailer downlink #1. Tables needs updated for downlink #1. Downlink #1 has also 2 more downlinks, downlink #2 and #3. Tables for downlinks #2 and #3 has to be added into the system and needs to be updated in the same way as downlink #1 table is updated. By default actions, larger dupe ring detection is impossible as the database actions are as fast as possible. Mail flow thru the FTN mailers are someway delayed. Proposed large dupe ring detection: Sending Test pings, that aren't included into the database ? and delayed upto the receiving from another FTN mailer ? (delayed database transfer actions on mails on continous schedules?) If sometimes the cluster node insert into database process of a single mail will be delayed, the mailflow thru the FTN mailer ring starts and ends up on the same cluster node or another cluster node, the information of the dupe ring can be detected. Using this mechanism, is an option in detecting dupe rings and further prevention of dupes by setting the related FTN mailer downlink to import or export state only. But the problem on this idea is, the mails that are used as test ping needs to be production mails to be tossed into the mail databases of all FTN downlinks to get them passed thru. ;& so that sending test ping mails have to use production mails ... i.e. monthly rules posting ?!? Sending test pings in the cluster node synchronisation is no problem, but sending test pings thru FTN downlinks tossers, that aren't aware of special 'test ping' mails is a problem. Solution search: Adding a X-TEST kludge to such a mail? (added X-TEST: 002002440112000000091009113800 to one mail) If a rules posting is received at one cluster node, the rules posting will be added the delayed action - meaning, waiting 24 hours to send out to the next downlink, awaiting next receive, send to the next downlink, wait again 24 hours and so on upto the last downlink (adding different X-TEST kludges to different downlinks? to identify late distributions thru other channels?!?). If once a mail with an X-TEST is received by a cluster node, this X-TEST kludge can be identified to a special test mail sent to downlink 1, received from downlink 2, so between downlink 1 and downlink 2 exists a dupe ring and the path can be read from the mail received from downlink 2 .... Area info will be great, added to the X-TEST kludge ... so it has to read (field-length): X-TEST: [area(1-n)]-[zone(3)][net(5)][node(5)][point(5)][year(2)][month(2)][day(2)][hour(2)][minute(2)][seconds(2)][[optional random number]] sample: X-TEST: fidocon.bleichenbach.1996-002002440112000000091009113800 to be continued ... Path Analysesample: FIDOCON.BLEICHENBACH.1996
PATHS: Maintain and report PATHS a message takes within an echo.
Copyright (C) 1991-1992, Graham J Stair. All rights reserved.
Release 2a for DOS (10th January 1993, 21:21) {-? for help}
Checked on : Wed Oct 07 18:04:20 2009
Number of nodes : 23
Number of messages : 344xx
Earliest message : Nov 27 2008
Latest message : Feb 05 2009 22:28:16 2106
2:244/1120 (6 of -31120)
+->2:244/1120.2 (784 of 784)
|
+->2:240/4030 (4983 of 4983)
|
+->2:244/1120.6 (2066 of 2066)
|
+->2:244/1117 (1371 of 1371)
|
+->2:240/2188.262 (9401 of 9401)
|
+->2:2443/1313 (0 of 5490) -------+
| +->2:280/5003 (19 of 2988) |
| | +->2:280/5003.4 (2967 of 2967) |
| | +->2:280/5555 (2 of 2) |
| | | |
| | +->2:280/5004 (0)
| | |
| +->2432/200 (0 of 168) -----+ |
| | +->2:2448/44 (0 of 167) | |
| | | +->2:2448/44.23 (167 of 167) | |
| | | V V
| | +->2:2432/390 (1 of 1) ? ?
| | | (+->2:240/2188 (0 of 9401) ???)
| | ???
| | | -------> 2:240/5832 ?
| | | -------> 2:2437/33 ?
| | SeenBy
| | +->2:24/905
| | +->2:240/2188
| | +->2:240/5778
| | +->2:244/1200
| | +->2:249/3110
| | +->2:313/41
| | +->2:423/81
| | +->2:2411/413
| | +->2:2432/0
| | +->2:2432/201
| | +->2:2432/215
| | +->2:2432/300
| | +->2:2433/401
| | +->2:2437/40
| | +->2:2443/1311
| | +->2:2452/250
| |
| |
| +->2:2443/1313.13 (1139 of 1139)
| |
| +->2:2443/1313.666 (6 of 6)
| |
| +->2:2443/1313.1168 (29 of 29)
| |
| +->1/2443 (14 of 14)
| |
| +->2:2443/1313.80 (4 of 4)
| |
| +->2:2443/1313.87 (3 of 3)
| |
| ???
|
+->2:244/1120.21 (9868 of 9868)
|
+->2:244/1120.23 (1586 of 1586)
+---------------------------------------------------------------------+
Average msg hops: 1.9 Maximum msg hops: 4
+---------------------------------------------------------------------+
The DOS timepacking problemAs in the history plain old DOS software is used and timestamps are packed with the DOS timepack algorhytm, timestamps with the 2 second difference could be a problem in syncing two databases. So the proposal is, to convert all timestamps to timestamps with even seconds. Every timestamp conversion then needs to be filtered thru the 2 seconds correction routine. Timestamp A: 2009-10-03 10:28:02 -> OK. Timestamp B: 2009-10-03 10:28:01 -> needs conversion to 2009-10-03 10:28:02 Note from KvE:
Alternates?SoftwareAn alternate can be the PhFiTo project at SourceForge.net. A PHP tosser project with multiple ftn api's
This is a part of PhFiTo (aka PHP Fido Tosser)
Copyright (c) Alex Kocharin, 2:50/13
This program is distributed under GNU GPL v2
See docs/license for details
$Id: phfito.php,v 1.13 2008/03/18 22:31:28 kocharin Exp $
API's included in this package:
Database Replycation, SynchronisationWiki SyncMLSyncML Schema SyncML PHP project SyncML Toolkits Synchronize MySQL Databases with PHPSynchronize multiple MySQL Databases with PHP
| |||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||