Auth0-js with Angular 2 (RC5), Webpack and CLI - javascript

I'm trying to implement auth0 into my Angular 2 project, and I don't want to use the lock widget but instead customize my own login form and buttons for social login. So I want to use the auth0-library on it's own. And I want it to be bundled, so not import it in index.html.
I've used the CLI to scaffold my project (1.0.0-beta.11-webpack.2) and installed auth0-js with NPM. I can find the 'auth0-js'-folder in my node_modules, now I just have to connect it to my app somehow.
// login.component
import { Component } from '#angular/core';
import * as Auth0 from "auth0-js";
#Component({
selector: 'app-login',
templateUrl: 'login.component.html',
styleUrls: ['login.component.css']
})
export class LoginComponent implements OnInit {
auth0: any;
constructor() {
this.auth0 = new Auth0({
domain: 'myDomain',
clientID: 'myClientId',
callbackURL: '{http://localhost:4000/}', // in dev-mode
callbackOnLocationHash: true
});
}
loginWithGoogle(connection) {
this.auth0.login({
connection: 'google-oauth2'
});
}
}
But I get this console message from Webpack:
ERROR in [default] ......... /node_modules/#types/auth0-js/index.d.ts' is not a module.
It seems the app is working, although the typings doesn't work. I've installed with npm i #types/auth0-js --save and it installs the typings to my node modules as expected.
Seems it's something wrong with the typings, but what? And is it something I can fix myself or do I have to wait until someone updates the typings to be modular?
Thanks!!

I have not used Auth0. But I think this should work.
main.ts
import 'auth0-js/standalone';
// Add this to test it.
var auth0 = new Auth0({
domain: 'mine.auth0.com',
clientID: 'dsa7d77dsa7d7',
callbackURL: 'http://my-app.com/callback',
responseType: 'token'
});
Quick typings work around src/typings.d.ts
declare var Auth0: any;
A better way to do typings:
Install the auth0 typings https://www.npmjs.com/package/#types/auth0
Update your tsconfig "types": ["auth0"]

Related

How to change text in the component base on the project I runs?

I build auth lib in my nx monorepo.
The auth lib contains LoginComponent (smart) and LoginFormComponent (dumb).
And I load the lib as lazy by using loadChildren to load auth.module and inside this module I have a child route to the LoginComponent which have LoginFormComponent.
Inside the LoginFormComponent I have text: "Login to my awesome app".
<h1>Login to my awesome app</h1>
<form...>
The problem is when I want to add another angular application and use this auth components and functionality.
So when I use the auth from the new application, I'm getting the text: "Login to my awesome app".
For the existing app the text should be: "Login to my awesome app".
And for new app should be: "Login to ng app".
I have only one auth lib with one of login component.
So I looking for angular way to deal with such senario.
I was think about duplicate the component but it's not feel right. or to use i18n but not sure because it's for langs, or using forRoot and pass the providers with the text? using tokens with inject?
What the ways I can do to change the text? How to handle this issue? is it solution to angular for this senario?
I can understand your situation. Here is what you should do. I am assuming that you have created a #shared/auth lib under nx monorepo. The auth lib contains the LoginFormComponent.
You should exploit ForRoot and #Inject() to achieve the same.
auth.module.ts
#NgModule({
// all imports etc
})
export class AuthModule {
static forRoot(appName: string): ModuleWithProviders<AuthModule> {
return {
ngModule: AuthModule,
providers: [
{ provide: APP_NAME, useValue: appName }
],
};
}
}
To avoid any circular dependency while importing APP_NAME, create a file as
config.ts
export const APP_NAME = new InjectionToken<string>('APP_NAME_PARAM');
Lets go your LoginFormComponent
LoginFormComponent.component.ts
export class LoginFormComponent{
public appName: string;
constructor(#Inject(APP_NAME) clientAppName: string){
this.appName = clientAppName;
}
}
login.component.html
<h1>Login to {{appName}} app</h1>
Now, we are all set. Only thing left to do, is to use AuthModule in our app.module.ts
app.module.ts
#NgModule({
imports: [
AuthModule.forRoot("Super Awesome")
]
})
export class AppModule
This can help you reuse the AuthModule in other apps as well. You just need create a constant file for each app library and then move Super Awesome into that constant for better readability.
It may not be completely relevant but, you can check this article for more understanding of ForRoot and InjectionToken
I have extensively used it in my Nx monorepo projects. Its a standard way.

Firebase Remote config (angular)

i am trying to use Firebase Remote Config. For the other services they provide there is a wrapper:
angularfire
However i can seem to see that Remote config is supported?
So following the documentation i have made the following service:
import {Injectable} from '#angular/core';
import {FirebaseConfig} from '#ionic-native/firebase-config/ngx';
#Injectable({
providedIn: 'root'
})
export class TextService {
constructor(private firebaseConfig: FirebaseConfig) {
this.firebaseConfig.getString('language_da').then((result) => {
console.log(result);
}).catch((error) => {
console.log(error);
});
}
}
However this gives me an inject error:
core.js:9110 ERROR Error: Uncaught (in promise): NullInjectorError: StaticInjectorError(AppModule)[FirebaseConfig]:
StaticInjectorError(Platform: core)[FirebaseConfig]:
NullInjectorError: No provider for FirebaseConfig!
Can anyone tell me the correct way of using Remote config ?
Your import is not correct:
import { FirebaseConfig } from '#ionic-native/firebase-config';
constructor(private firebaseConfig: FirebaseConfig) { }
And just to be sure Install the Cordova and Ionic Native plugins:
$ ionic cordova plugin add cordova-plugin-firebase-config
$ npm install --save #ionic-native/firebase-config#4

How do I declare a dependency on an ng-metadata module?

I have a project that is using ng-metadata (https://github.com/ngParty/ng-metadata) to build a handful of Angular 1.5 modules. I have a test module/component that looks like this:
import { NgModule, Component, Inject, Input, Output, EventEmitter } from 'ng-metadata/core'
import { platformBrowserDynamic } from 'ng-metadata/platform-browser-dynamic'
#Component({
selector: 'test',
template: require('./test.template.html')
})
class TestComponent {
#Input() type: string;
constructor() {
console.log(`test: ${this.type}`)
}
}
#NgModule({
declarations: [TestComponent]
})
class HeroModule {}
platformBrowserDynamic().bootstrapModule(HeroModule)
Everything seems happy when compiled and I'm now attempting to use the module in another project (that is not using ng-metadata but has a compatible version of Angular).
I'm simply including the shims as directed by the ng-metadata docs and the JavaScript file that contains the module described above (built by webpack). I have a new module in this project that wants to list the HeroModule as a dependency. I've tried a few things:
// attempt 1:
angular.module('my-consuming-module', ['ui.router', 'hero'])
// attempt 2:
angular.module('my-consuming-module', ['ui.router', 'heroModule'])
// attempt 3:
angular.module('my-consuming-module', ['ui.router', 'hero-module'])
All always end up with the same Error: $injector:nomod Module Unavailable error from Angular.
If I'm using ng-metadata to build my modules, what are the names I use to list them as dependencies in another project?
Finally figured this out! It's amazing what happens when you carefully read documentation...
Found in the Manual Angular 1 Bootstrap section of ng-metadata's docs:
You can still leverage ng2 way of components registration without ng-metadata bootstrap, but you have to manually create your Angular 1 module from an ng-metadata #NgModule using the bundle helper function.
I ended up being able to do the following:
// REMOVED platformBrowserDynamic().bootstrapModule(HeroModule)
const Ng1AdminModule = bundle(HeroModule).name;
export const AppModule = angular.module('hero', [Ng1AdminModule]);
And then my hero module becomes accessible to the my-consuming-module just as I expected. The bundle helper function was the key to figuring this out.
You need to import those module from their respective locations and inject it inside your angular module
//ensure `angular`, `angular-ui-router` should be there in `map` of systemjs.config.js
import * as angular from 'angular';
import * as uiRouter from 'angular-ui-router';
import { heroModule} from './hero.module';
angular.module('app',[ uiRouter, heroModule]);
Check references here

NPM module "only refers to a type, but is being used as a value here." in Ionic 2 / Angular 2

I'm trying to import the npm module "ajv" into my Ionic 2 (Angular 2) project. (https://epoberezkin.github.io/ajv/)
I ran "npm install ajv --save", then made the following changes to my app.modules.js file:
import { Ajv } from 'ajv';
...
providers : [
Ajv,
...
]
When I compile, however, I get the error:
'Ajv' only refers to a type, but is being used as a value here.
c:/Users/me/Documents/Ionic/MyApp/src/app/app.module.ts
Is there a better way to pull in this library?
The providers array in NgModule is for use with #Injectable components or similarly functional "providers" or "services" in other speak. This library does not appear to conform to that design.
It's likely that all you really want to do is use the import within your application component, rather than in AppModule. By import I mean the simple ES6 style import of "symbol" and then direct usage in code.
So for example in example.component.ts:
import { Component } from '#angular/core';
import { Ajv } from 'ajv';
#Component({
selector: 'app-example',
templateUrl: './example.component.html',
styleUrls: ['./example.component.css']
})
export class ExampleComponent {
myMethod() {
// Just use Ajv here
}
}
No need to put this in the decorator arrays.
If an imported third party library is rather something you want to use in a "service like manner", then by all means wrap it as an #Injectable service, but the consumption will stay much the same as the the above example.

Trying to integrate braintree-web into Angular2

I am trying to use the Braintree SDK (braintree-web) in my Angular2 app. I'd really appreciate any pointers on how to get this working. I think it is because I am not importing the braintree-web module, but I can't figure out how to to that either. I can find any exports in the whole module.
Here is where I am:
I've imported the braintree-web library and a typings file I found.
ng install --save braintree-web
npm install #types/braintree-web#3.0.1
I tried to hack the JS example Braintree provides into a Angular2 TS Component, but I keep getting an error:
EXCEPTION: Error: Uncaught (in promise): EXCEPTION: Error in
./UpaccountComponent class UpaccountComponent - inline template:5:7
ORIGINAL EXCEPTION: TypeError: this.braintree.setup is not a function
Here is the .ts file.
import { Component, OnInit } from '#angular/core';
declare var braintree:any;
#Component({
selector: 'up-btcheckoutform',
templateUrl: './btcheckoutform.component.html',
styleUrls: ['./btcheckoutform.component.css']
})
export class BtCheckoutFormComponent implements OnInit {
braintree = require('BrainTreeWeb');
// braintree = require('braintree-web');
integration: any
constructor() { }
ngOnInit() {
var c = this;
var clientToken = "CLIENT_TOKEN_GOES_HERE";
braintree.setup(clientToken, "dropin", {
container: "payment-form",
onReady: function(int) {
c.integration = int
}
});
}
ngOnDestroy() {
this.integration.teardown();
}
}
I'm not sure about the usage of braintree-web specifically, but if you're using webpack, remove the lines declare var braintree:any; and braintree = require('BrainTreeWeb');
You'll also need to add the braintree-web/index.js file to the bundle, unless they've got a UMD module.
From a quick glance at braintree-web, it looks like braintree.setup(..) isn't a function. Something like this might be equivalent:
braintree.client.create({
authorization: "long-token-string"},
(err, client) => {
// Do stuff here
client.request({..});
});
With the package installs, you'll need to have added --save-dev to the types install.
I have integrated the brain-tree the same way as you have done and it works.
I've just installed one more command
first install
npm install #types/braintree-web#3.0.1er
then install
npm install --save braintree-web#2.30.0
and use
braintree = require('braintree-web');
Again if it asks for braintree is not defined then remove declare var braintree:any;
and replace bellow code
braintree.setup(clientToken, "dropin", {
container: "payment-form",
onReady: function(int) {
c.integration = int
}
});
with
this.braintree.setup(clientToken, "dropin", {
this.container: "payment-form",
onReady: function(int) {
c.integration = int
}
});
Edit:
just declare the var after import declare var braintree:any; if your working with angular 4 then declare declare var require: any;
You can also import it via:
import * as braintree from 'braintree-web';
Refer this:
Refrring 3rd party JS libraries in angular 2
It's a universal solution. You don't even need to use any npm packages. Just simply refer BrainTree JS libarary in index.html and follow the steps documented in above link. It's applicable for any JS library.

Categories