Phonegap-plugin-push's on.('notification') doesn't fire - javascript

I'm trying to implement push-notification in my hybrid app, which is built with reactjs and cordova, using phonegap-plugin-push.
i have setup everything correctly (added the plugin, registered with firebase, the google-services.js file is in the right place).
i put this in my index.js file:
import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
import App from './App';
import * as serviceWorker from './serviceWorker';
// ReactDOM.render(<App />, document.getElementById('root'));
// If you want your app to work offline and load faster, you can change
// unregister() to register() below. Note this comes with some pitfalls.
// Learn more about service workers:
const startApp = () => {
ReactDOM.render(
<App />,
document.getElementById('root')
);
serviceWorker.unregister();
var push = window.PushNotification.init({
android:{}
});
console.log(push);
push.on('registration', function (data) {
console.log("on registration");
console.log(data);
});
push.on('notification', function (data) {
// console.log("notification received");
alert("Title:"+data.title+" Message:"+ data.message);
});
push.on('error', function (e) {
console.log(e.message)
});
}
if(!window.cordova) {
console.log("cordova is null");
startApp();
} else {
document.addEventListener('deviceready', startApp, false);
}
when i run the app on android emulator, and debug it using the chrome inspect devices, i can see the on('registration') is fired and work properly. But when i try to send a notification from firebase to the device, nothing happen.
This is how i compose my notification:
*Notification title(optional): title
Notification text: test noti
Notification label: test noti
*Target
App com.allen.thomas.netdi //the package name that i registered
*Scheduling
i chose "send now"
*Conversion events(optional)
didn't do anything with this
*Additional options(optional)
//left the Android "Notification Channel" field blank
//For custom data I filled in the following keys-values
title Test Notification
body Please work!
badge 1
content-available 1
priority: high
sound: enabled
expires: 4 weeks
then i hitted publish. But nothing happened. I don't understand what is the problem here?

Does your packagename match with the project in firebase?
Have you enabled Android Support Repository version 47+ in Android Studio?
See: https://github.com/phonegap/phonegap-plugin-push/blob/master/docs/INSTALLATION.md#android-details

It seems that i figure out the solution to this. All i need to do was adding these lines of code inside the on('notification) 's callback function:
push.finish(function(){
console.log("notification received successfully");
})
It solve my problem.

Related

Integrate Countly SDK Web with Typescript

Has anyone here has experience integrating Countly SDK Web with ReactJS using Typescript?
The example given here assume people use Javascript to use the SDK. I want to do something like.
import { Countly } from 'countly-sdk-web';
and use it to hit some API that has been created in Countly when webpage load. Any help would be greatly appreciated.
Note: The files is in .tsx extension
you can reach an example on how to integrate Countly Web SDK in a ReactJS project from here.
Again there, a basic example to import Countly would be like this:
import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
import App from './App-WithEffect';
import * as serviceWorker from './serviceWorker';
import Countly from 'countly-sdk-web';
//Exposing Countly to the DOM as a global variable
//Usecase - Heatmaps
window.Countly = Countly;
Countly.init({
app_key: 'YOUR_APP_KEY',
url: 'YOUR_SERVER_URL',
session_update: 10,
use_session_cookie: true,
debug: false,
require_consent: true,
namespace: "react-demo",
inactivity_time: 1,
offline_mode: false,
// device_id: "cly-device-demo-id" //Set only if you want dont want to use countly generated device_id
});
//Since Countly is loaded and available, you can use synchronus or asynchronus calls, does not matter
Countly.q.push(['group_features', {
activity: ["sessions", "events", "views", "location"],
interaction: ["scrolls", "clicks", "crashes"],
whereabouts: ["users"]
}]);
if (typeof(localStorage) !== "undefined") {
var consents = localStorage.getItem("consents");
if(consents){
Countly.q.push(['add_consent', JSON.parse(consents)]);
}
else{
var consent = window.confirm("We are going to track you. Do you give your consent ?");
consents = ["activity", "interaction", "whereabouts"];
if(consent) {
Countly.q.push(['add_consent', consents]);
localStorage.setItem("consents", JSON.stringify(consents));
}
else {
Countly.q.push(['remove_consent', consents]);
localStorage.removeItem("consents");
}
}
}
Countly.q.push(['enableRatingWidgets', {'widgets': ['widget-id-1','widget-id-2']}]);
Countly.q.push(['track_sessions']);
Countly.q.push(['track_scrolls']);
Countly.q.push(['track_clicks']);
Countly.q.push(['track_links']);
Countly.q.push(["track_errors"]);
ReactDOM.render(
<React.StrictMode>
<App />
</React.StrictMode>,
document.getElementById('root')
);
// If you want your app to work offline and load faster, you can change
// unregister() to register() below. Note this comes with some pitfalls.
serviceWorker.unregister();
You can reach this code from here

Code for passing user information from azureAD to app.js

I am trying to introduce the Single-Sign-On (SSO) feature to my React app and I want to use the user information from my company for the SSO verification. For that, I registered my application on the Azure website to acquire the clientID. I have found an article that shows how to make use of React AAD MSAL package to enable user login through a popup method: https://www.npmjs.com/package/react-aad-msal .
I create an authProvider.js file with the following code:
// authProvider.js
import { MsalAuthProvider, LoginType } from 'react-aad-msal';
// Msal Configurations
const config = {
auth: {
authority: 'https://login.microsoftonline.com/common',
clientId: 'XXXXXXXXXXXXXXXXXXXXXXX',
redirectUri: 'localhost:3000'
},
cache: {
cacheLocation: "localStorage",
storeAuthStateInCookie: true
}
};
// Authentication Parameters
const authenticationParameters = {
scopes: [
'User.Read'
]
}
// Options
const options = {
loginType: LoginType.Popup,
tokenRefreshUri: window.location.origin + '/auth.html'
}
export const authProvider = new MsalAuthProvider(config, authenticationParameters, options)
and my index.js file looks like this:
// index.js
import React from 'react';
import ReactDOM from 'react-dom';
import { BrowserRouter } from 'react-router-dom';
import { AzureAD } from 'react-aad-msal';
import App from './App';
import { authProvider } from './authProvider';
ReactDOM.render(
<BrowserRouter>
<AzureAD provider={authProvider} forceLogin={true}>
<App />
</AzureAD>
<BrowserRouter>,
document.getElementById('root'),
);
This code worked and allowed me to authenticate users on the sign in and then redirected them to the redirect URL. I now would like to pass user information such as name, surname, email address and profile picture to the App component.
I was not able to find resources online that would help me do it and the documentation on the npm website does not have examples of that being done. Could anyone provide working code examples of how to do what I want? (All my files are in js and I can not use any code examples provided by Microsoft as they use tsx files and I don't want to change all my files to TypeScript).
Perhaps there are some children or property functions in MsalAuthProvider that I can call but I could not find documentation on that function either. I am also not sure of where to call these functions in index.js so code examples would be very helpful. Thanks
You could get user information with myMSALObj.getAccount() using MSAL.js.
const myMSALObj = new Msal.UserAgentApplication(msalConfig);
function signIn() {
myMSALObj.loginPopup(loginRequest)
.then(loginResponse => {
console.log('id_token acquired at: ' + new Date().toString());
console.log(loginResponse);
if (myMSALObj.getAccount()) {
showWelcomeMessage(myMSALObj.getAccount());
}
}).catch(error => {
console.log(error);
});
}
For more details about the code sample, see here.
Also you could get access token in your code with react-aad-msal. Some information of the user such as username and email will be shown after decoding the token.
import jwtDecode from 'jwt-decode';
const claims = jwtDecode('base64 encoded token received from Azure AD');

Office Add-ins excel extension is not working on IE11 with 'import axios' statement

I'm currently developing a Excel extension for my company with Office Add-ins and Reactjs.
Lately I've been using Axios in order to make http requests to get data from a remote back-end service. The issue is that the statement "import axios from 'axios'" is not handled in IE11 and the application runs into an exception when this statement is present in a script file. The exception is :
Office.js has not fully loaded. Your app must call "Office.onReady()" as part of it's loading sequence (or set the "Office.initialize" function). In itself that doesn't say a lot except that "the code does not compile".
After a few researches on my own I discovered that IE11 needs polyfill in order to make it work since it doesn't natively support the most recent js scripts (ES6, promises by example).
I've tried many kinds of combinations with babel/polyfill, react-app-polyfill, es-promise with no result so far. Happily, in a another application I've been working on recently (VueJs with axios), I met the same problem and just adding 'import babel/polyfill' did the trick.
I would like to know if anyone has succeeded in doing what I am trying to do for a few days and if not, any help will be appreciated. Some of my coworkers are using Windows 7 or Windows Server 2019 and I really need this excel extension to function with IE11.
Thank you for your help.
Edit on 06/29 :
Here is what I have in my index.js :
import "office-ui-fabric-react/dist/css/fabric.min.css";
import App from "./components/App";
import { AppContainer } from "react-hot-loader";
import { initializeIcons } from "office-ui-fabric-react/lib/Icons";
import * as React from "react";
import * as ReactDOM from "react-dom";
/* global AppCpntainer, Component, document, Office, module, React, require */
initializeIcons();
let isOfficeInitialized = false;
const title = "Contoso Task Pane Add-in";
const render = Component => {
ReactDOM.render(
<AppContainer>
<Component title={title} isOfficeInitialized={isOfficeInitialized} />
</AppContainer>,
document.getElementById("container")
);
};
Office.initialize = () => {
isOfficeInitialized = true;
render(App);
};
render(App);
if (module.hot) {
module.hot.accept("./components/App", () => {
const NextApp = require("./components/App").default;
render(NextApp);
});
}
commands.js : You can see that I have a commented import statement in this file regarding axios. My intent is to make it work in the dataservice instead but I put that statement here just for testing purpose. The dataservice class itself has only one dependency : axios.
import "babel-polyfill";
// import axios from 'axios';
import DataService from '../server/dataservice';

React PWA - enforce update on click

community,
I am doing "programmatic presentations" using React (CLI) and PWA (register()). Everything works just fine, but anytime some changes are made, the URL of the final app needs to be changed so all changes are loaded.
The whole mechanism works like this:
The final app is sent to Github,
this private repo is connected to Netlify,
Netlify generates a unique URL,
users visit this Netlify URL and hit "add to home screen" on iPad,
the whole app runs under the Safari engine.
If any change in the code is made, I have to change the link in Netlify and send this new link to a people.
The process mentioned above works just fine, but honestly, it would be nice to have some kind of functionality that allows request latest update on demand - let's say - on click of a button.
Is something like that possible?
Thank you for comments!
Kind Regards
Linc
At serviceWorker.js file can find this code
if (config && config.onUpdate) {
config.onUpdate(registration);
}
So implement the config.onUpdate funtion
Create a file swConfig.js
export default {
onUpdate: registration => {
registration.unregister().then(() => {
window.location.reload()
})
},
}
At index.js send the implement function to serviceWorker
import React from 'react';
import ReactDOM from 'react-dom';
import './index.css';
import App from './App';
import * as serviceWorker from './serviceWorker';
import swConfig from './swConfig'
ReactDOM.render(<App />,
document.getElementById('root'));
serviceWorker.register(swConfig);
Check out this repo
https://github.com/wgod58/create_react_app_pwaupdate
If you want to control the update with a button click, I did using the following snippet:
Note: If your app must work offline, you should add some extra logic to verify if the user has internet connection, as the following code would break the app if it's unable to fetch the service-worker.
import React from 'react';
function App(){
const updateApp = () => {
if ('serviceWorker' in navigator) {
navigator.serviceWorker.ready.then((registration) => {
registration.unregister().then(() => {
window.location.reload();
});
});
}}
return(
<div style={{margin:"auto"}}>
<button onClick={updateApp}>
Update App
</button>
</div>
);
}
https://gist.github.com/juliomilani/6492312d1eb657d06b13c9b87d5ad023

Relay's Inject Network Layer Not Being Recognized as a Function in a React App

I am following along a Lynda.com tutorial called "Building and Deploying a Full-Stack React Application", and in the chapter "Injecting the Relay Network Layer" there is in index.js, an attempt to set up a network layer, and the program compiles successfully but I'm receiving the following error in the browser:
TypeError: __WEBPACK_IMPORTED_MODULE_4_react_relay___default.a.injectNetworkLayer is not a function
Any ideas?
I'd appreciate it,
CM
(My index.js file)
import React from 'react'
import ReactDOM from 'react-dom'
import {Router, browserHistory, applyRouterMiddleware} from 'react-router'
import Routes from './routes'
import Relay from 'react-relay'
import useRelay from 'react-router-relay'
import {RelayNetworkLayer, urlMiddleware} from 'react-relay-network-layer'
import {relayApi} from './config/endpoints'
import auth from './utils/auth'
const createHeaders = () => {
let idToken = auth.getToken()
if (idToken) {
return {
'Authorization': `Bearer ${idToken}`
}
} else {
return {}
}
}
Relay.injectNetworkLayer(
new RelayNetworkLayer([
urlMiddleware({url: (req) => relayApi,}),
next => req => {
req.headers = {
...req.headers,
...createHeaders()
}
return next(req)
},
],{disableBatchQuery: true})
)
ReactDOM.render(
<Router
environment={Relay.Store}
render={applyRouterMiddleware(useRelay)}
history={browserHistory}
routes={Routes}
/>,
document.getElementById('root')
)
You are probably not using the right version of Relay, but its just a guess. Check if the tutorial specifies any version and check which one you are using.
A lot of things changed in the last version of Relay: Relay-Modern. You might want to look into that, its way more convenient and efficient than Relay-Classic.
Also there are easier ways to combine a router with relay. Create your Relay Environment directly above or below your router, depending on if you need to get routes out of your db. But I guess you just need to get through the tutorial.

Categories

Resources