Skip to content

Instantly share code, notes, and snippets.

@pavan-idapalapati
Created February 13, 2019 13:18
Show Gist options
  • Save pavan-idapalapati/609e4a0da9d24a946265b31244058cc0 to your computer and use it in GitHub Desktop.
Save pavan-idapalapati/609e4a0da9d24a946265b31244058cc0 to your computer and use it in GitHub Desktop.
import { combineLatest as observableCombineLatest, of as observableOf, Observable } from 'rxjs';
import { mergeMap, catchError, map, tap } from 'rxjs/operators';
import { Injectable } from '@angular/core';
import { locationService } from './location.service';
import { ApiCallsService } from './apicalls.service';
import * as moment from 'moment';
// import 'moment-timezone';
import { constants } from '../modules/utilities/constants';
// import { communicationService } from './communication.service';
// import { Observable, ReplaySubject, BehaviorSubject } from 'rxjs';
// import { Subject } from 'rxjs/Subject';
@Injectable()
export class dateService {
dateSettings: any;
dateAPicallData;
sub_dateSettings: any;
locationData: any;
moment: any;
locationOffsets: any = {};
constructor(
// private communicationService : communicationService
private location: locationService,
private apiCallsService: ApiCallsService,
private constants: constants
) {
this.getDateSettings().subscribe(() => {
//
});
this.moment = moment;
}
getDateSettings() {
if (!this.sub_dateSettings) {
this.sub_dateSettings = this.location
.getLocation()
.pipe(
mergeMap((data: any) => {
let date = new Date();
let location = data.location;
if (location) {
// Get timezone considering daylight time savings
return this.getLocalTimeConsideringDayLightSavings({
date: date,
latitude: location.latitude,
longitude: location.longitude
});
} else {
return Observable.create((observer) =>
observer.next({
date: {
value: this.getLocalTimeWithoutConsideringDayLightSavings(
date
)
},
useLocaltime: true
})
);
}
}),
map((data: any) => {
this.dateSettings = data;
})
)
.pipe(
catchError((e) => {
let date = new Date();
this.dateSettings = {
date: this.getLocalTimeWithoutConsideringDayLightSavings(date),
useLocaltime: true
};
return Observable.create((observer) => observer.next(this.dateSettings));
})
);
}
return this.sub_dateSettings;
}
convertToUTC(date: Date) {
let toUTCString = date.toUTCString();
return this.convertToStandardServerFormat(toUTCString);
}
convertToStandardServerFormat(dateUTCString: string) {}
convertToLocalTime(str) {
let result: any = {};
let isRe = /(\d{2}:\d{2} (AM|PM) .{3,4})/;
if (isRe.test(str)) {
// Sometimes from backend the time is coming in 24 hour format though the AM/PM is mentioned
// So, normalizing the string
str = str.replace(/\d{2}/, ('00' + ((+str.match(/\d{2}/)[0] % 12) + '')).slice(-2));
let localTime = str.match(isRe)[1];
let currentDate = new Date();
let currentDateString = currentDate.toString();
// let tzAbbr = this.getLocalTimezoneAbbr(currentDateString);
let re = /(\w{3} \w{3} \d{2} \d{4} )(\d{2}:\d{2}:\d{2} \w{3})(.+$)/;
let changedTimeString = currentDateString.replace(re, (a, x, y, z) => x + localTime);
let changedDate: any = new Date(changedTimeString);
let changedTime = this.getTimeFormat(changedDate);
let currentDay = currentDate.getDay() + 1;
let changedDay = changedDate.getDay() + 1;
result.date = changedDate;
result.time = changedTime;
result.changedStr = str.replace(/(\d{2}:\d{2} (AM|PM) .{3})/, result.time);
} else {
result.changedStr = str;
result.time = str;
result.date = new Date();
}
return result;
}
getLocalTimezoneAbbr(dateString) {
let match = dateString.match(/\((.*)\)/);
if (match) {
return match[1]
.split(' ')
.map((m) => m.substring(0, 1))
.join('');
}
}
getTimeFormat(date) {
// return moment(date).tz(moment.tz.guess()).format('hh:mm A z');
return moment(date).format('LT') + ' ' + this.getLocalTimezoneAbbr(date.toString());
}
getLocal(date: Date): Observable<any> {
let $this = this;
date = $this.convertToDate(date);
if (date) {
return $this.location.getLocation().pipe(
mergeMap((data: any) => {
let location = data.location;
if (location) {
// Get timezone considering daylight time savings
return observableOf(
$this.getLocalTimeConsideringDayLightSavings({
date: date,
latitude: location.latitude,
longitude: location.longitude
})
);
} else {
// Get timezone without considering daylight time savings
return Observable.create((observer) => {
return observer.next({
date: $this.getLocalTimeWithoutConsideringDayLightSavings(date)
});
});
}
})
);
} else {
// return Observable.empty<Response>();
return Observable.create((observer) => {
return observer.next(null);
});
}
}
private convertToDate(rawDate) {
if (typeof rawDate === 'string') {
return new Date(rawDate);
}
return rawDate;
}
public getLocalTimeConsideringDayLightSavings(payload: any): Observable<any> {
let timestamp = payload.date.getTime() / 1000 + payload.date.getTimezoneOffset() * 60;
if (!this.dateAPicallData) {
this.dateAPicallData = this.getTimeBasedOnLocation(payload);
return this.dateAPicallData;
} else if (this.locationData) {
return this.formedLocationData({
timestamp: timestamp
});
} else {
// This case executes when the datesettings observable hasn't yet got response
// So, hold the execution till the datesettings comes up
return this.dateAPicallData.flatMap(() =>
this.formedLocationData({
timestamp: timestamp
})
);
}
}
public getTimeBasedOnLocation(payload) {
payload.apiKey = 'AIzaSyATQwr7_9YNC7bzXDk7EIYzaVqGLkYyOrs';
// reference from http://www.javascriptkit.com/dhtmltutors/local-time-google-time-zone-api.shtml
let timestamp = payload.date.getTime() / 1000 + payload.date.getTimezoneOffset() * 60;
let date = payload.date.toISOString();
let url = `https://maps.googleapis.com/maps/api/timezone/json?location=${
payload.latitude
},${payload.longitude}&timestamp=${timestamp}&key=${payload.apiKey}`;
return this.apiCallsService
.doCall({
url: url,
local: true,
noHeaders: true
})
.pipe(
map((data) => {
data.localTime = (data.dstOffset + data.rawOffset + timestamp) * 1000;
data.date = new Date(data.localTime);
data.time = moment(data.date).format('hh:mm A z');
data.useLocaltime = false;
let tz_abbr = '';
data.timeZoneName.split(' ').map((name) => {
tz_abbr = tz_abbr + name.charAt(0);
});
data.tz_abbr = tz_abbr;
this.locationData = data;
return data;
})
)
.pipe(
catchError((e) => {
console.log(e + ' ' + 'timetest');
return Observable.create((observer) =>
observer.next({
date: this.getLocalTimeWithoutConsideringDayLightSavings(payload.date),
useLocaltime: true
})
);
})
);
}
formedLocationData(payload) {
let timestamp = payload.timestamp;
this.locationData.localTime =
(this.locationData.dstOffset + this.locationData.rawOffset + timestamp) * 1000;
this.locationData.date = new Date(this.locationData.localTime);
this.locationData.useLocaltime = false;
let tz_abbr = '';
this.locationData.timeZoneName.split(' ').map((name) => {
tz_abbr = tz_abbr + name.charAt(0);
});
this.locationData.tz_abbr = tz_abbr;
return observableOf(this.locationData);
}
private getLocalTimeWithoutConsideringDayLightSavings(date) {
return new Date(date);
}
getLocalDateAndTime(utcTime, noSeconds?): any {
//note IE is not supporting normal date converion because of that we are passing here moment object.
utcTime = moment(utcTime);
let date = this.getLocalTimeWithoutConsideringDayLightSavings(utcTime);
return this.formatDate(date, noSeconds);
}
formatDate(date, noSeconds?) {
let localDate;
let localTimestamp;
let localTime;
let timestamp = date.getTime() / 1000 + date.getTimezoneOffset() * 60;
localDate = date;
localTimestamp = timestamp * 1000;
localTime = this.getTimeFormat(localDate);
let formattedDateTime = {
timeStamp: localTimestamp, // @WARNING: This is a UTC timestamp
date: localDate.toLocaleDateString(),
time: localTime,
dateObj: date
};
return formattedDateTime;
}
public addTimeZoneTime(timeStamp, timezoneData) {
console.log('----------------------------------------------');
console.log('patient-time offset:', timezoneData.rawOffset);
timeStamp = this.getLocalTimeWithoutConsideringDayLightSavings(timeStamp);
let result = moment(timeStamp)
.clone()
.add(timezoneData.dstOffset + timezoneData.rawOffset, 'seconds')
.utc()
.format();
console.log('After adding offset', result);
console.log('----------------------------------------------');
return result;
}
public convertToOtherTimezone(payload) {
// payload
// - dates (Array of dateStrings)
// - removeTimezone
// -- lat
// -- long
// -- offset
// -- system (Boolean): If this is present, none of the above are necessary
// - addTimezone
// -- lat
// -- long
// -- offset (if this is present, then lat and long are not necessary)
// -- system (Boolean): If this is present, none of the above are necessary
//
let this$ = this;
function getOffset(obj: any): Observable<any> {
let date: Date = new Date();
if (obj.system) {
return observableOf(date.getTimezoneOffset() * -60);
} else if (obj.offset !== undefined) {
// To handle the case when offset is 0
return observableOf(+obj.offset);
} else {
// Assuming left over is lat and long
// Get the offset through available lat and long
return this$
.getTimeBasedOnLocation({
date: date,
latitude: obj.lat,
longitude: obj.long
})
.pipe(
mergeMap((data) => {
// form the offset
let offset = data.dstOffset + data.rawOffset;
this$.locationOffsets[obj.lat + obj.long] = offset;
return observableOf(offset);
})
);
}
}
return observableCombineLatest([
getOffset(payload.removeTimezone),
getOffset(payload.addTimezone)
]).pipe(
mergeMap(([removeTimezone, addTimezone]) => {
// Logic to remember: Remove the removeTimezone and Add the addTimezone
// This works even if the removeTimezone or addTimezone are negative values
var adjustOffset = -removeTimezone + addTimezone;
var convertedDates = payload.dates.map((date) => {
return moment(date)
.clone()
.add(adjustOffset, 'seconds')
.utc()
.format();
});
return Observable.create((obs) => obs.next(convertedDates));
})
);
}
/**
* This function is used to get the nearset 15 minutes.
*/
public getNearestTime(date?) {
let condiondate = date ? new Date(date) : new Date();
let result = 0;
let quarterTime = 15;
let minutes = 60;
let loop = minutes / quarterTime;
let mins = condiondate.getMinutes();
if (mins % quarterTime == 0) {
return 0;
}
for (let i = 1; i <= loop; i++) {
let q_mins = i * quarterTime;
if (mins <= q_mins) {
result = q_mins - mins;
break;
}
}
return result;
}
public combineDateTime(date, time) {
// date = new Date(date).toLocaleDateString();
// time = moment(time).format('LT');
let formatedDate = date.format('MM/DD/YYYY');
let dateObj = moment(new Date(formatedDate + ' ' + time));
return dateObj.utc().format();
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment