11const roleDAO = require ( "../dao/roleDao" ) ;
2- const locationDAO = require ( "../dao/locationDAO" ) ;
32const loggingDAO = require ( "../dao/loggingDao" ) ;
43const followerDAO = require ( "../dao/followerDao" ) ;
54const wizardDAO = require ( "../dao/wizardDao" ) ;
5+ const clockFaceController = require ( "../controllers/clockFaceController" ) ;
6+ const locationDAO = require ( "../dao/locationDAO" ) ;
7+ const clockFaceDAO = require ( "../dao/clockFaceDao" ) ;
8+ const dobby = require ( "./discordController" ) ;
9+ const settingsService = require ( "../controllers/serverSettingController" ) . default . getInstance ( ) ;
610
711async function addUserInfo ( username , password , role , isFollower , leadID ) {
8- const defaultLocation = await locationDAO . getDefaultLocation ( ) ;
12+ const defaultPosition = await clockFaceController . getDefaultClockPosition ( ) ;
913 await wizardDAO . addUser ( username , password , role , isFollower ) . then ( async ( ) => {
1014 let newUser = await wizardDAO . getUserFromName ( username )
1115 await roleDAO . addUserToRole ( newUser . id , role ) ;
12- await wizardDAO . setUserLocation ( newUser . id , defaultLocation . id ) ;
16+ await wizardDAO . setUserClockPosition ( newUser . id , defaultPosition . id ) ;
1317 if ( isFollower ) {
1418 await updateUserToFollower ( newUser . id , leadID ) ;
1519 }
@@ -38,8 +42,107 @@ async function updateUserInfo(user) {
3842 return true ;
3943}
4044
45+ async function handleUserLocationUpdate ( userID , coords , isHeartbeat ) {
46+ const locations = await locationDAO . getAllLocations ( ) ;
47+ const followerIDList = [ ] ;
48+
49+ // Check for Followers
50+ await followerDAO . getFollowerInfoFromLeadID ( userID ) . then ( results => {
51+ for ( let followInfo of results ) {
52+ followerIDList . push ( followInfo . follower_id ) ;
53+ }
54+ } ) ;
55+
56+ // Update Location Logs
57+ await loggingDAO . updateUserLocationLog ( userID , coords . latitude , coords . longitude ) ;
58+ if ( followerIDList . length > 0 ) {
59+ for ( let followerID of followerIDList ) {
60+ await loggingDAO . updateUserLocationLog ( followerID , coords . latitude , coords . longitude ) ;
61+ }
62+ }
63+
64+ for ( let location of locations ) {
65+ if ( isUserWithinLocation ( coords . latitude , coords . longitude , location . latitude , location . longitude , location . radius ) ) {
66+ let clockPosition = await clockFaceController . getClockPositionFromLocationID ( location . id ) ;
67+ await fireLocationUpdate ( userID , clockPosition , isHeartbeat ) ;
68+ await wizardDAO . updateUserClockPosition ( userID , clockPosition . id ) . catch ( ( ) => {
69+ return false ;
70+ } ) ;
71+ if ( followerIDList . length > 0 ) {
72+ await updateFollowersClockPosition ( followerIDList , clockPosition . id ) ;
73+ }
74+ return true ;
75+ }
76+ }
77+
78+ const defaultClockPosition = await clockFaceController . getDefaultClockPosition ( ) ;
79+ await fireLocationUpdate ( userID , defaultClockPosition , isHeartbeat ) ;
80+ await wizardDAO . updateUserClockPosition ( userID , defaultClockPosition . id ) . catch ( ( ) => {
81+ return false ;
82+ } ) ;
83+ if ( followerIDList . length > 0 ) {
84+ await updateFollowersClockPosition ( followerIDList , defaultClockPosition . id ) ;
85+ }
86+ return true ;
87+ }
88+
89+ async function updateFollowersClockPosition ( followers , clockPositionID ) {
90+ const clockPosition = clockFaceDAO . getClockPositionFromID ( clockPositionID ) ;
91+ for ( let followerID of followers ) {
92+ await fireLocationUpdate ( followerID , clockPosition , null ) ;
93+ await wizardDAO . updateUserClockPosition ( followerID , clockPositionID ) ;
94+ }
95+ }
96+
97+ async function fireLocationUpdate ( userID , clockPosition , isHeartbeat ) {
98+ if ( settingsService . getSettingValue ( "notifyEveryPositionUpdate" ) === "true" ) {
99+ await sendDiscordPing ( userID , clockPosition , isHeartbeat ) ;
100+ } else {
101+ const userClockPosition = await clockFaceController . getClockPositionFromUserID ( userID ) ;
102+ if ( userClockPosition . face_position !== clockPosition . face_position ) {
103+ await sendDiscordPing ( userID , clockPosition , isHeartbeat ) ;
104+ }
105+ }
106+ }
107+
108+ async function sendDiscordPing ( userID , clockPosition , isHeartbeat ) {
109+ await wizardDAO . getUserFromID ( userID ) . then ( async ( result ) => {
110+ if ( result . isFollower === "false" ) {
111+ await dobby . notifyLocationChange ( result . username , clockPosition . name , isHeartbeat ) ;
112+ } else {
113+ let leadID = await followerDAO . getLeadIDFromFollowerID ( result . id ) ;
114+ let lead = await wizardDAO . getUserFromID ( leadID . lead_id ) ;
115+ await dobby . notifyFollowerLocationChange ( result . username , lead . username , clockPosition . name ) ;
116+ }
117+ } ) ;
118+ }
119+
120+ function isUserWithinLocation ( userLat , userLong , locationLat , locationLong , radius ) {
121+ return getDistanceFromLatLonInM ( userLat , userLong , locationLat , locationLong ) <= radius ;
122+ }
123+
124+ // From https://stackoverflow.com/a/27943
125+ function getDistanceFromLatLonInM ( userLat , userLong , locationLat , locationLong ) {
126+ var R = 6371 ; // Radius of the earth in km
127+ var dLat = deg2rad ( locationLat - userLat ) ; // deg2rad below
128+ var dLon = deg2rad ( locationLong - userLong ) ;
129+ var a =
130+ Math . sin ( dLat / 2 ) * Math . sin ( dLat / 2 ) +
131+ Math . cos ( deg2rad ( userLat ) ) * Math . cos ( deg2rad ( locationLat ) ) *
132+ Math . sin ( dLon / 2 ) * Math . sin ( dLon / 2 )
133+ ;
134+ var c = 2 * Math . atan2 ( Math . sqrt ( a ) , Math . sqrt ( 1 - a ) ) ;
135+ var d = R * c ; // Distance in km
136+ return d * 1000 ; // Convert to m
137+ }
138+
139+ function deg2rad ( deg ) {
140+ return deg * ( Math . PI / 180 )
141+ }
142+
143+
41144async function deleteUserInfo ( userID ) {
42- await wizardDAO . deleteUserLocation ( userID ) ;
145+ await wizardDAO . deleteUserClockPosition ( userID ) ;
43146 await loggingDAO . clearUserLocationLog ( userID ) ;
44147 await roleDAO . removeUserFromRole ( userID ) ;
45148 await wizardDAO . getUserFromID ( userID ) . then ( async user => {
@@ -54,9 +157,9 @@ async function deleteUserInfo(userID){
54157
55158async function updateUserToFollower ( followerID , leadID ) {
56159 await followerDAO . applyFollowLink ( followerID , leadID ) ;
57- await wizardDAO . getUserLocationFromUserID ( leadID ) . then ( async ( locationInfo ) => {
58- if ( locationInfo ) {
59- await wizardDAO . setUserLocation ( followerID , locationInfo . location_id ) ;
160+ await wizardDAO . getUserClockPositionInfoFromUserID ( leadID ) . then ( async ( clockPositionInfo ) => {
161+ if ( clockPositionInfo ) {
162+ await wizardDAO . setUserClockPosition ( followerID , clockPositionInfo . position_id ) ;
60163 }
61164 } )
62165}
@@ -80,5 +183,6 @@ async function removeLeadFromFollowers(userID) {
80183module . exports = {
81184 addUserInfo,
82185 updateUserInfo,
83- deleteUserInfo
186+ deleteUserInfo,
187+ handleUserLocationUpdate
84188} ;
0 commit comments