Could not Detect Online Connectivity in Angular 11 - angular11

I tried to show online status in angular 11.
I did same as like this https://dzone.com/articles/how-to-detect-the-internet-connection-status-in-an
My ts.file
import { ConnectionService } from 'ng-connection-service';
isConnected = true;
noInternetConnection: boolean;
constructor(private connectionService: ConnectionService,) {
this.connectionService.monitor().subscribe(isConnected => {
this.isConnected = isConnected;
if (this.isConnected) {
this.noInternetConnection=false;
}
else {
this.noInternetConnection=true;
}
})
}
my.html file
<nb-action *ngIf="noInternetConnection">
<p>online</p>
</nb-action>
<nb-action *ngIf="!noInternetConnection">
<p>offline</p>
</nb-action>
BUT it shows offline. MY wifi connection is on
Can anyone help me to find the bug?

I personally don't recommend to use another library to listen for native browser events as this makes the application more robust, and probably the library does the same as the following code :(
When I achived such functionality I created event listeners for the native "online" and "offline" events.
Here is the network monitor service.
import { Injectable } from '#angular/core';
import { fromEvent, ReplaySubject } from 'rxjs';
import { distinctUntilChanged } from 'rxjs/operators';
#Injectable()
export class NetworkStatusService {
private init: boolean = navigator.onLine;
private online: ReplaySubject<boolean> = new ReplaySubject();
get initStatus() {
return this.init
}
constructor() {
if (this.init==false) {
this.online.next(false);
}
fromEvent(window, "online").subscribe((val) => {
this.online.next(true);
})
fromEvent(window, "offline").subscribe((val) => {
this.online.next(false);
})
}
getOnlineStatus() {
return this.online.pipe(distinctUntilChanged());
}
}

Related

how to show id, compliantype in angular 7 with using asp.net core web api>

i am using asp.net core web api for backend and angular 7 for front end .i created database using code first
approach and then i added one more table called Complains .now i wan to return complains table id and two or three more columns from complains table using get request. then get these values in angular and show some where .
//this is interface method
Object UserComplainInformation(Complains complains);
//this is service class which implements above interface
public Object UserComplainInformation(Complains complains)
{
var resp = new
{
Id = _appDbContext.Complains.FindAsync(complains.Id),
Type =complains.Type
};
try
{
_appDbContext.Complains.FindAsync(resp);
return resp;
}
catch(Exception ex)
{
throw ex;
}
//Controller
[HttpGet]
// [Route("complainInformation")]
public Object UserComplainInformation(Complains complain)
{
return _complains.UserComplainInformation(complain);
}
//angular service code
import { Injectable } from '#angular/core';
import { ToastrService } from 'ngx-toastr';
import { ConfigService } from './util/config.service';
import { HttpClient } from '#angular/common/http';
#Injectable({
providedIn: 'root'
})
export class ComplainHistoryService {
BaseUrl : string ='';
constructor( private config:ConfigService, private http:HttpClient) {
this.BaseUrl =config.getApiURI();
}
ngOnInit(){ }
getUserComplainHistory(){
return this.http.get(this.BaseUrl +'/complianInformation');
}
}
//.ts file usercomplainhistory
import { Component, OnInit } from '#angular/core';
import { Router } from '#angular/router';
import { ComplianHistoryService } from 'src/shared/complain-history.service';
#Component({
selector: 'app-user-complians-history',
templateUrl: './user-complains-history.component.html',
styles: []
})
export class UserComplainsHistoryComponent implements OnInit {
userDetails = sessionStorage.getItem('FullName');
userComplainDetails;
constructor(private router:Router, private complainService: ComplainHistoryService) { }
ngOnInit() {
this.complainService.getUserComplainHistory().subscribe(
res =>{
this.userComplainDetails = res;
console.log(res);
},
err =>{
console.error(err);
}
)
}
}
//this is html file where i want to show id and some more fields
<ul class="list-group">
<li class="list-group-item"><strong>FullName : </strong>{{userDetails}}</li>
<li class="list-group-item"><strong>Complian Id : </strong>{{userComplianDetails}}</li>
</ul>

Return firebase values from a service to a component angular 6

I'm creating an application with angular 6 and firebase using angularfire2, I chose to use the firestore where I have a collection called pages like in the image:
basically I created a service - "PagesService" where I have a function that returns the data of the page that I sent. I'm trying to use getPage to return the values to my component, and assign them to the form, nothing else I tried worked, only returns an "observable" that I can not work, does anyone have an idea of what I can do?
Full code, service:
import { Injectable } from '#angular/core';
import { AngularFirestore, AngularFirestoreCollection, AngularFirestoreDocument } from 'angularfire2/firestore';
import { Observable } from 'rxjs';
import { map } from 'rxjs/operators';
#Injectable()
export class PagesService {
private pagesCollection: AngularFirestoreCollection<any>;
private page: AngularFirestoreDocument<any>;
constructor(private afs: AngularFirestore) {
this.pagesCollection = afs.collection('pages');
}
getPage(pageName: string) {
return this.afs.doc<any>('pages/${pageName}').valueChanges();
}
addPages(pageName: string, pageForm: any) {
this.pagesCollection.doc(pageName).set(pageForm.value);
}
}
My component:
import { Component, OnInit } from '#angular/core';
import { FormBuilder, FormGroup } from '#angular/forms';
import { Observable } from 'rxjs';
import { PagesService } from '../../services/pages.service';
#Component({
selector: 'app-quem-somos',
templateUrl: './quem-somos.component.html',
styleUrls: ['./quem-somos.component.scss']
})
export class QuemSomosComponent implements OnInit {
pageForm: FormGroup;
pageName: string = "wo-we-are";
page: any;
constructor(private pagesService: PagesService, private fb: FormBuilder) { }
ngOnInit() {
this.page = this.pagesService.getPage(this.pageName);
console.log(this.page);
this.pageForm = this.fb.group({
title: '',
content: ''
});
}
save() {
this.pagesService.addPages(this.pageName, this.pageForm);
}
}
obs: Sorry my english
If I have understand you right, When you say "Observable that I cannot work" is mean that you cannot access his data when you are trying to assign its values in the form?
In this case (I assume that your service is working as expected), just subscribe to it and populate the form after your values are ready to use. for example:
ngOnInit() {
this.pagesService.getPage(this.pageName).subscribe(v => {
// Here your data is ready, so you can send it to a function and populate the form as you need.
this.populateForm(v);
});
// Here I just construct the FormGroup, so your application can rendered.
this.pageForm = this.fb.group({
title: '',
content: ''
});
}
And add this function to do the task:
populateForm = (data) => {
console.log(data); // Just log it in console, and see if its the data that you seek for
}
Instead of console.log() you can populate your form or do what ever you need to.
Good Luck !
--EDIT--
I just noticed now, In your service:
getPage(pageName: string) {
return this.afs.doc<any>('pages/${pageName}').valueChanges();
}
You call the doc with ' ' instead of ``, so In fact, you are not using Template Strings. So your call is wrong and not fetch with the right path.
Change it to:
return this.afs.doc<any>(`pages/${pageName}`).valueChanges();

Angular 5 - Http Interceptor and behavior Subject Issue

I am facing issue when i am using http interceptors(to intercept the http request and response) and behvior subject ( for communication between 2 services based on the interceptors) . I have a scenario where i need to monitor all the http calls going on in the application and make a specific http post call only when there are no other http calls are going in the application .
I have interceptor service where i am intercepting all the http request and responses and when no call is happening ,counter variable is 0 then , using a behavior subject ok$ ,and subscribing it in the other Service 2 and from there making a specific http post call . This subscribing is not happening second time , when the value of ok$ is changed.
Interceptor service :
import { Injectable } from '#angular/core';
import { HttpResponse, HttpEvent, HttpClient, HttpHeaders, HttpInterceptor, HttpHandler, HttpRequest, HttpErrorResponse } from '#angular/common/http';
import { BehaviorSubject } from 'rxjs';
import 'rxjs/add/operator/do';
#Injectable()
export class InterceptorService {
counter: number = 0;
public ok$: BehaviorSubject<any>;
constructor() {
this.ok$ = new BehaviorSubject(false);
}
checkCounter() {
if (this.counter === 0) {
setTimeout(() => {
this.checkCounterFinally();
}, 1000);
}
}
checkCounterFinally() {
if (this.counter === 0) {
this.ok$.next(true);
}
}
intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
if (this.counter === -1)
this.counter = 1;
else
this.counter++;
return next.handle(req).do(
(event: HttpEvent<any>) => {
if (event instanceof HttpResponse) {
console.log(event);
this.counter--;
this.checkCounter();
}
},
(error: any) => {
(event instanceof HttpErrorResponse)
{
if (error instanceof HttpErrorResponse) {
if (error.status != 200) {
console.log(error);
}
}
}
}
);
}
}
Service 2: Making Rest call :
import { Injectable } from '#angular/core';
import { LogService } from '../common/log.service';
import { HttpClient, HttpHeaders } from '#angular/common/http';
import { Observable, BehaviorSubject } from 'rxjs';
import { InterceptorService } from './interceptor.service';
#Injectable()
export class WorkerService {
data: string;
storage = this.LogService.storage;
RestUrl = // some url
constructor(private service1: LogService, private httpClient: HttpClient,
private interceptor: InterceptorService) {
this.service1.logData.subscribe((val) => {
this.storage.setItem("key", "value");
});
this.interceptor.ok$.subscribe((value) => {
if (value === true) {
this.getDataFromLocalStorage();
}
});
}
getDataFromLocalStorage(): void {
//getting data from the local storage and making rest call to server
}
pushDatatoServer(data: string) {
this.httpClient.post(this.RestUrl, this.data, this.httpHeaderObjRequestParam )
.subscribe((response) => {
// do something
}
}
}

ExpressionChangedAfterItHasBeenCheckedError in Directive with Angular

After I get all the hate, I know there's a thread about this problem but I haven't managed to find a solution for my problem. I'm a rookie.
What I wanted to do was to change the nav header background only when the user is in a particular route, so I created a directive in which I retrieve the current url and then I styled the nav header with setElementStyle. For that I'm comparing if the current url matches a particular url that I store in a variable.
The app is working fine but I still get that error.
This is my directive:
import {Directive, ElementRef, Renderer, OnInit, ChangeDetectorRef} from '#angular/core';
import { Router, NavigationStart, NavigationEnd, NavigationError, NavigationCancel, RoutesRecognized } from '#angular/router';
import 'rxjs/add/operator/filter';
#Directive({
selector: '[styled]',
})
export class StyledDirective implements OnInit {
constructor(public el: ElementRef, public renderer: Renderer, public _router: Router) {
renderer.setElementStyle(el.nativeElement, 'color', '#212121');
renderer.setElementStyle(el.nativeElement, 'backgroundColor', 'rgb(247, 247, 247)');
}
ngOnInit(){
const profileUrl = "/app/userprofile";
this._router.events
.filter(event => event instanceof NavigationStart)
.subscribe((event:NavigationStart) => {
if (event.url == profileUrl) {
return this.el.nativeElement.style.backgroundColor = '#ffffff';
}
else {
return this.el.nativeElement.style.backgroundColor = 'rgb(247, 247, 247)';
}
});
this._router.events
.filter(event => event instanceof NavigationStart)
.subscribe((event:NavigationStart) => {
if (event.url == profileUrl) {
return this.el.nativeElement.style.color = "#03A9F4";
}
else {
return this.el.nativeElement.style.color = '#212121';
}
});
}
}
Probably its not the best code ever but that's how I tried to resolve my problem, and probably there's a more elegant solution for this. Thanks for your help guys!
I prefer this way
First inject the Router in constructor, then return a function according to route
constructor(private router: Router) {}
getRoute(){
if (this.router.url === '/client'){
return "client";
}
}
in your html
<header [ngClass]="getRoute()">
and in css
header.client{background-color:yellow}

Network Check and show Toast on Http Request

I am very new to ionic, currently working/learning with Ionic 2. I would like to show a toast when a user goes offline. I am currently able to do that as shown in my code below (toast shows whenever user goes offline). However what i would like to do is show the toast on http request (pull to refresh and infinite scroll). So that even when data is already loaded, the toast gets displayed when the user tries to pull to refresh on load more data through infinite scroll then they get notified that they are offline.
export class HomePage {
datas:any = [];
page:number =1;
connected: Subscription;
disconnected: Subscription;
constructor(private toast: ToastController, private network: Network, public navCtrl: NavController, private wpapi: Wpapi) {
this.getPosts();
}
displayNetworkUpdate(connectionState: string){
//let networkType = this.network.type
this.toast.create({
message: `You are currently ${connectionState}, please re connect your data`,
duration: 3000
}).present();
}
ionViewDidEnter() {
this.disconnected = this.network.onDisconnect().subscribe(data => {
console.log(data)
this.displayNetworkUpdate(data.type);
}, error => console.error(error));
}
getPosts() {
//this.page = '1';
//this.wpapi.index(this.page)
this.wpapi.index(1)
.subscribe(data => {
this.datas = data;
console.log(this.datas);
});
}
loadMore(infiniteScroll) {
this.page++;
this.wpapi.index( this.page ).subscribe( datas => {
// Loads posts from WordPress API
let length = datas["length"];
if( length === 0 ) {
infiniteScroll.complete();
return;
}
for (var i = length - 1; i >= 0; i--) {
this.datas.push( datas[i] );
}
infiniteScroll.complete();
});
}
doRefresh(refresher) {
this.wpapi.index(1)
.subscribe(data => {
this.datas = data;
refresher.complete();
});
}
ionViewWillLeave(){
this.connected.unsubscribe();
this.disconnected.unsubscribe();
}
}
This is what i'm doing. In my app.components i have the connection subscriber, beeing it offline or online, so if a user goes offline i save a conn boolean variable with false, if online i save true in my localStorage and present a toast saying it has gone offline (if gone online there's no need to present a toast).
network.onDisconnect().subscribe(() => {
storage.set('conn', false);
let conoff = ToastCtrl.create({
closeButtonText: 'Ok',
showCloseButton: true,
message: 'You're not connected to internet.',
position: 'top'
});
conoff.present();
});
You can create a service to do this, something like
import { Injectable } from '#angular/core';
import { Storage } from '#ionic/storage';
import { ToastController, Platform } from 'ionic-angular';
#Injectable()
export class Verificador {
constructor(public toast: ToastController, public storage: Storage, public platform: Platform) {
}
verifyConnection = (): Promise<boolean> => {
return new Promise<boolean>((res, rej) => {
this.storage.get('conn').then(conn => {
if (conn) {
res(true);
} else {
let t = this.toast.create({
closeButtonText: 'Ok',
showCloseButton: true,
message: 'You can't do this without internet.',
position: 'top'
});
t.present();
res(false);
}
})
})
}
}
So in every component, page entering, http call, you import that service/provider and call the verifyConnection function, if it returns true you just let the user do what it needs to do, if it's false the provider will show the toast.
import { ConnVerification} from '../../../providers/ConnVerification';
#IonicPage()
#Component({
selector: 'your-page',
templateUrl: 'your-page',
providers: [ConnVerification]
})
export class YourPage {
constructor(public verif: ConnVerification){}
myFunctionForSomething(){
this.verif.verifyConnection().then(conn =>{
if(conn){
// DO YOUR CODE
}
// NO NEED FOR ELSE SINCE IT'S HANDLED ON PROVIDER
})
}
}
Hope it helps :)

Resources