This guide walks you through integrating OneSDK with a new Angular project, providing a robust foundation for building KYC/AML features in your Angular application.

Quick Setup

1

Install Angular CLI

$npm install -g @angular/cli
2

Create New Angular Project

$ng new <project-name>
3

Install OneSDK Package

$npm install @frankieone/one-sdk

Webpack Configuration

1

Install Dependencies

$npm install -D @angular-builders/custom-webpack file-loader style-loader css-loader @types/react
2

Update angular.json

Add custom Webpack configuration:

1{
2 "projects": {
3 "<project-name>": {
4 "architect": {
5 "build": {
6 "builder": "@angular-builders/custom-webpack:browser",
7 "options": {
8 "customWebpackConfig": {
9 "path": "./webpack.config.js"
10 }
11 }
12 },
13 "serve": {
14 "builder": "@angular-builders/custom-webpack:dev-server"
15 }
16 }
17 }
18 }
19}
3

Create webpack.config.js

1module.exports = {
2 module: {
3 rules: [
4 {
5 test: /\.svg$/,
6 use: [
7 {
8 loader: "file-loader",
9 options: {
10 name: "assets/[name].[hash:8].[ext]",
11 },
12 },
13 ],
14 },
15 {
16 test: /\.css$/,
17 use: [{ loader: "style-loader" }, { loader: "css-loader" }],
18 exclude: /src/,
19 },
20 ],
21 },
22};

TypeScript Configuration

Update your tsconfig.json or tsconfig.app.json:

1{
2 "compilerOptions": {
3 "allowSyntheticDefaultImports": true,
4 "skipLibCheck": true
5 }
6}

Implementation

app.component.ts
1@Component({
2 selector: 'app-root',
3 templateUrl: './app.component.html'
4})
5export class AppComponent implements OnInit {
6 async ngOnInit() {
7 await this.initializeOneSDK();
8 }
9
10 private async initializeOneSDK() {
11 const session = await this.getSessionToken();
12 const oneSdk = await this.setupSDK(session);
13 await this.configureSDK(oneSdk);
14 }
15
16 private async getSessionToken() {
17 const config = {
18 CUSTOMER_ID: '',
19 CUSTOMER_CHILD_ID: '',
20 API_KEY: ''
21 };
22
23 const response = await fetch(
24 "https://backend.latest.frankiefinancial.io/auth/v2/machine-session",
25 {
26 method: "POST",
27 headers: {
28 authorization: "machine " + btoa([
29 config.CUSTOMER_ID,
30 config.CUSTOMER_CHILD_ID,
31 config.API_KEY
32 ].filter(Boolean).join(":")),
33 "Content-Type": "application/json"
34 },
35 body: JSON.stringify({
36 permissions: {
37 preset: "one-sdk",
38 reference: `demo-${new Date().toISOString()}`
39 }
40 })
41 }
42 );
43
44 return response.json();
45 }
46
47 private async setupSDK(session: any) {
48 return await OneSDK({
49 session,
50 recipe: {
51 form: {
52 provider: {
53 name: 'react',
54 googleApiKey: "YOUR_GOOGLE_API_KEY"
55 },
56 }
57 }
58 });
59 }
60
61 private async configureSDK(oneSdk: any) {
62 // Setup event logging
63 oneSdk.on('*', console.log);
64
65 // Initialize individual flow
66 const individual = oneSdk.individual();
67 await this.setupConsent(individual);
68
69 // Configure IDV flow
70 await this.setupIDVFlow(oneSdk);
71 }
72
73 private async setupConsent(individual: any) {
74 individual.addConsent("general");
75 individual.addConsent("docs");
76 individual.addConsent("creditheader");
77 await individual.submit();
78 }
79
80 private async setupIDVFlow(oneSdk: any) {
81 const component = oneSdk.component as unknown as (arg0: any, arg1?: any) => any;
82 const flow = oneSdk.flow as unknown as (arg0: any) => any;
83
84 const idv = flow("idv");
85 const loading1 = component("form", {
86 name: "LOADING",
87 title: { label: "Loading..." },
88 descriptions: [{ label: "" }]
89 });
90
91 const loading2 = component("form", {
92 name: "LOADING",
93 title: { label: "Processing results..." },
94 descriptions: [{
95 label: "Hold tight, this can take up to 30 seconds. Please don't refresh this page."
96 }]
97 });
98
99 const review = component("form", {
100 name: "REVIEW",
101 type: "ocr"
102 });
103
104 this.setupIDVEventHandlers(idv, loading1, loading2, review);
105 idv.mount("#e2e-idv-container");
106 }
107
108 private setupIDVEventHandlers(idv: any, loading1: any, loading2: any, review: any) {
109 let before = true;
110
111 idv.on("loading", (display: boolean) => {
112 if (display && before) {
113 loading1.mount("#e2e-idv-loading1");
114 } else if (before) {
115 loading1.unmount();
116 before = false;
117 }
118 });
119
120 idv.on("results", async ({ checkStatus }: { checkStatus: boolean }) => {
121 if (checkStatus) {
122 loading2.unmount();
123 review.mount("#e2e-idv-container");
124 }
125 });
126
127 idv.on("detection_complete", () => {
128 loading2.mount("#e2e-idv-loading2");
129 });
130
131 // Error handling
132 idv.on("error", ({ message, payload }: { message: string, payload: any }) => {
133 console.error("IDV Error:", message, payload);
134 });
135 }
136}

Running the Application

1

Start Development Server

$npm run start
2

Access Application

Open your browser and navigate to http://localhost:4200

Security Note

Never store API keys or credentials in your frontend code. Use environment variables and a secure backend service to handle authentication.

Troubleshooting

  • Webpack Configuration Errors: Ensure all loaders are properly configured in webpack.config.js
  • TypeScript Errors: Verify tsconfig.json settings, especially allowSyntheticDefaultImports
  • Component Mounting Issues: Check if container IDs match in both component and template files
  • Use environment variables for API keys and endpoints
  • Implement proper error handling for API calls
  • Follow Angular’s lifecycle hooks for initialization
  • Implement proper cleanup in ngOnDestroy
Need Help?

If you encounter issues, check our sample code repository or reach out to our support team.

Built with