Can't get Plaid Link to Open using Javascript and python - javascript

When the plaid link handler is called it spins and then goes away. I can't get the link dialog box to show completely to get access token. Setup using flask for the python server on port 5000 and using the plaid api for calls in python. Using javascript on the client side.
I can see the requests going through but nothing happens or seems to post to the client:
127.0.0.1 - - [05/Apr/2022 21:53:31] "GET / HTTP/1.1" 200 -
127.0.0.1 - - [05/Apr/2022 21:54:10] "GET / HTTP/1.1" 200 -
127.0.0.1 - - [05/Apr/2022 21:54:10] "POST /create_link_token HTTP/1.1" 200 -
Javascript:
<!DOCTYPE html>
<html>
<head>
</head>
<body>
<button id="link-button">Link Account</button>
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/3.5.1/jquery.min.js"></script>
<script src="https://cdn.plaid.com/link/v2/stable/link-initialize.js"></script>
<script type="text/javascript">
(async function($) {
var handler = Plaid.create({
// Create a new link_token to initialize Link
token: (await $.post('/create_link_token')).link_token,
receivedRedirectUri: window.location.href,
onLoad: function() {
// Optional, called when Link loads
},
onSuccess: function(public_token, metadata) {
// Send the public_token to your app server.
// The metadata object contains info about the institution the
// user selected and the account ID or IDs, if the
// Account Select view is enabled.
$.post('/exchange_public_token', {
public_token: public_token,
});
},
onExit: function(err, metadata) {
// The user exited the Link flow.
if (err != null) {
// The user encountered a Plaid API error prior to exiting.
}
// metadata contains information about the institution
// that the user selected and the most recent API request IDs.
// Storing this information can be helpful for support.
},
onEvent: function(eventName, metadata) {
// Optionally capture Link flow events, streamed through
// this callback as your users connect an Item to Plaid.
// For example:
// eventName = "TRANSITION_VIEW"
// metadata = {
// link_session_id: "123-abc",
// mfa_type: "questions",
// timestamp: "2017-09-14T14:42:19.350Z",
// view_name: "MFA",
// }
}
});
$('#link-button').on('click', function(e) {
handler.open();
});
})(jQuery);
</script>
</body>
</html>
Python server.py:
# source /Users/tnappy/node_projects/quickstart/python/bin/activate
# Read env vars from .env file
from plaid.exceptions import ApiException
from plaid.model.payment_amount import PaymentAmount
from plaid.model.payment_amount_currency import PaymentAmountCurrency
from plaid.model.products import Products
from plaid.model.country_code import CountryCode
from plaid.model.recipient_bacs_nullable import RecipientBACSNullable
from plaid.model.payment_initiation_address import PaymentInitiationAddress
from plaid.model.payment_initiation_recipient_create_request import PaymentInitiationRecipientCreateRequest
from plaid.model.payment_initiation_payment_create_request import PaymentInitiationPaymentCreateRequest
from plaid.model.payment_initiation_payment_get_request import PaymentInitiationPaymentGetRequest
from plaid.model.link_token_create_request_payment_initiation import LinkTokenCreateRequestPaymentInitiation
from plaid.model.item_public_token_exchange_request import ItemPublicTokenExchangeRequest
from plaid.model.link_token_create_request import LinkTokenCreateRequest
from plaid.model.link_token_create_request_user import LinkTokenCreateRequestUser
from plaid.model.asset_report_create_request import AssetReportCreateRequest
from plaid.model.asset_report_create_request_options import AssetReportCreateRequestOptions
from plaid.model.asset_report_user import AssetReportUser
from plaid.model.asset_report_get_request import AssetReportGetRequest
from plaid.model.asset_report_pdf_get_request import AssetReportPDFGetRequest
from plaid.model.auth_get_request import AuthGetRequest
from plaid.model.transactions_get_request import TransactionsGetRequest
from plaid.model.transactions_get_request_options import TransactionsGetRequestOptions
from plaid.model.identity_get_request import IdentityGetRequest
from plaid.model.investments_transactions_get_request_options import InvestmentsTransactionsGetRequestOptions
from plaid.model.investments_transactions_get_request import InvestmentsTransactionsGetRequest
from plaid.model.accounts_balance_get_request import AccountsBalanceGetRequest
from plaid.model.accounts_get_request import AccountsGetRequest
from plaid.model.investments_holdings_get_request import InvestmentsHoldingsGetRequest
from plaid.model.item_get_request import ItemGetRequest
from plaid.model.institutions_get_by_id_request import InstitutionsGetByIdRequest
from plaid.model.transfer_authorization_create_request import TransferAuthorizationCreateRequest
from plaid.model.transfer_create_request import TransferCreateRequest
from plaid.model.transfer_get_request import TransferGetRequest
from plaid.model.transfer_network import TransferNetwork
from plaid.model.transfer_type import TransferType
from plaid.model.transfer_user_in_request import TransferUserInRequest
from plaid.model.ach_class import ACHClass
from plaid.model.transfer_create_idempotency_key import TransferCreateIdempotencyKey
from plaid.model.transfer_user_address_in_request import TransferUserAddressInRequest
from plaid.api import plaid_api
from flask import Flask
from flask import render_template
from flask import request
from flask import jsonify
from datetime import datetime
from datetime import timedelta
import plaid
import base64
import os
import datetime
import json
import time
from dotenv import load_dotenv
from werkzeug.wrappers import response
import pyodbc
load_dotenv()
app = Flask(__name__)
cnxn = pyodbc.connect("Driver={SQL Server Native Client 11.0};"
"Server=DESKTOP-DJCMSVC\MJBOURQUIN_SQL;"
"Database=MyBudget;"
"Trusted_Connection=yes;")
cursor = cnxn.cursor()
cursor.execute('SELECT * FROM Accounts')
for row in cursor:
print('row = %r' % (row,))
vals = ("SOMETHING")
data = "UPDATE Accounts Set API_ID = 'SOMETHING' WHERE Id = 1"
cursor.execute(data)
cursor.commit();
access = "THAT THING"
cursor = cnxn.execute('UPDATE Accounts Set API_ID = ? WHERE Id = ?', [access,1])
cursor.commit();
# Fill in your Plaid API keys - https://dashboard.plaid.com/account/keys
PLAID_CLIENT_ID = os.getenv('PLAID_CLIENT_ID')
PLAID_SECRET = os.getenv('PLAID_SECRET')
# Use 'sandbox' to test with Plaid's Sandbox environment (username: user_good,
# password: pass_good)
# Use `development` to test with live users and credentials and `production`
# to go live
PLAID_ENV = os.getenv('PLAID_ENV', 'sandbox')
# PLAID_PRODUCTS is a comma-separated list of products to use when initializing
# Link. Note that this list must contain 'assets' in order for the app to be
# able to create and retrieve asset reports.
PLAID_PRODUCTS = os.getenv('PLAID_PRODUCTS', 'transactions').split(',')
# PLAID_COUNTRY_CODES is a comma-separated list of countries for which users
# will be able to select institutions from.
PLAID_COUNTRY_CODES = os.getenv('PLAID_COUNTRY_CODES', 'US').split(',')
products = []
for product in PLAID_PRODUCTS:
products.append(Products(product))
def empty_to_none(field):
value = os.getenv(field)
if value is None or len(value) == 0:
return None
return value
host = plaid.Environment.Sandbox
if PLAID_ENV == 'sandbox':
host = plaid.Environment.Sandbox
if PLAID_ENV == 'development':
host = plaid.Environment.Development
if PLAID_ENV == 'production':
host = plaid.Environment.Production
# Parameters used for the OAuth redirect Link flow.
#
# Set PLAID_REDIRECT_URI to 'http://localhost:3000/'
# The OAuth redirect flow requires an endpoint on the developer's website
# that the bank website should redirect to. You will need to configure
# this redirect URI for your client ID through the Plaid developer dashboard
# at https://dashboard.plaid.com/team/api.
PLAID_REDIRECT_URI = empty_to_none('PLAID_REDIRECT_URI')
configuration = plaid.Configuration(
host=host,
api_key={
'clientId': PLAID_CLIENT_ID,
'secret': PLAID_SECRET,
'plaidVersion': '2020-09-14'
}
)
api_client = plaid.ApiClient(configuration)
client = plaid_api.PlaidApi(api_client)
#app.route('/')
def index():
return render_template('index.html')
#app.route('/my-link/')
def my_link():
print ('I got clicked!')
return 'Click.'
#app.route("/create_link_token", methods=['POST'])
def create_link_token():
# Get the client_user_id by searching for the current user
request = LinkTokenCreateRequest(
products=products,
client_name="Budgetary",
country_codes=list(map(lambda x: CountryCode(x), PLAID_COUNTRY_CODES)),
language='en',
user=LinkTokenCreateRequestUser(
client_user_id=str(time.time())
)
)
if PLAID_REDIRECT_URI!=None:
request['redirect_uri']=PLAID_REDIRECT_URI
# create link token
response = client.link_token_create(request)
return jsonify(response.to_dict())
#app.route('/exchange_public_token', methods=['POST'])
def exchange_public_token():
global access_token
public_token = request.form['public_token']
request = ItemPublicTokenExchangeRequest(
public_token=public_token
)
response = client.item_public_token_exchange(request)
access_token = response['access_token']
item_id = response['item_id']
cursor = cnxn.execute('UPDATE Accounts Set API_ID = ? WHERE Id = ?', [access_token,1])
cursor.commit();
return jsonify(response.to_dict())
if __name__ == '__main__':
app.run(debug=True)

Solved by breaking the code out into pieces. Clicking the button, then requesting and printing value in python. Then sending and making sure it's parsed correctly. Then with the parsed token value opening up link successfully.

Related

How can I use main.dart variable in my JS file?

I'm trying to create a calling app using flutter and I've created the backend using a node.js. This is how my main.dart file in flutter looks like:
import 'package:flutter/material.dart';
import 'dart:async';
import 'dart:io';
import 'package:flutter/services.dart';
import 'package:flutter_dialpad/flutter_dialpad.dart';
import 'dart:js';
import 'package:js/js.dart';
void main() => runApp(MyApp());
class MyApp extends StatefulWidget {
#override
_MyAppState createState() => _MyAppState();
}
class _MyAppState extends State<MyApp> {
#override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
backgroundColor: Colors.black,
body: SafeArea(
child:
DialPad(
enableDtmf: true,
outputMask: "(000) 000-0000",
backspaceButtonIconColor: Colors.red,
makeCall: (number){
print(number);
}
)
),
),
);
}
}
I want to use this "number" variable in my app.js file which looks like this:
const accountSid = '***';
const authToken = '***';
const client = require('twilio')(accountSid, authToken);
client.calls.create({
url: 'http://demo.twilio.com/docs/voice.xml',
to: '+10000000',
from: '+1000000',
}, function(err, call){
if (err) {
console.log(err);
} else {
console.log(call.sid);
}
})
I want to be able to use the "number" variable from my main.dart file in the "to" field in my app.js file. Please help me out...
What you need is a way to pass data between applications, and the easiest way for that would be through a REST API
You can use the HTTP module in NodeJS or a third-party package like Express and set up a POST Route to your NodeJS Server, where the number is sent as data.
Once the data is received on your server, you can call your Twilio function, and send a response back.
On Flutter, you can use the http package to make the API call.

Displaying data is not possible in vue

I'm sending this data to the view part that is written in view but isn't displayed, do you think?
$itemsCount = DB::table('items')
->groupBy('level_id')
->selectRaw('level_id, count(*) as type');
$ItemsMdCount = DB::table('items')
->groupBy('project_model_id')
->selectRaw('project_model_id, count(*) as type');
return view('project.view', compact('users', 'itemsCount', 'itemsMdCount'));
And in vue I make the display {{ itemsCount }}
How can I send the data to Vue.js and display it?
I tried and with an AJAX request but I do not realize how to properly use axios. I do not use much vue and I still have concerns, if you can give me a tip how I could display with the first option would be super cool.
Route::get('/get-items-count-id/{modelId}', 'Ajax\AjaxController\getIemsCount')->name('getItemsCount');
Route::get('/get-items-md-count/{modelId}', 'Ajax\AjaxController\getItemsMdCount')->name('getItemsMdCount');
public function getItemsCount($modelId)
{
$itemsCount = Item::where('project_model_id', $modelId)
->groupBy('level_id')
->selectRaw('level_id, count(*) as type')->get();
return $this->successResponse($itemsCount);
}
public function getItemsMdCount($modelId)
{
$itemsMdCount = Item::where('project_model_id', $modelId)
->groupBy('project_model_id')
->selectRaw('project_model_id, count(*) as type')->get();
return $this->successResponse($itemsMdCount);
}
Follow these steps to include axios.
Step 1: npm install --save axios
Step 2: Create a 'axios-auth.js' file and paste this code
import axios from 'axios'
const instance = axios.create({
baseURL: 'http://localhost:3000'
});
export default instance
Step 3: Include import axios from './axios-auth' in store.js
Step 4: You can use vuex for API calls
Step 5: In the vuex Actions property you can call the API as shown below
signUp({ commit, dispatch }, authData) {
return axios.post('/register', authData)
}
Step 6: You can use
this.$store.dispatch('signUp', formData)
on the page from the API will be requested.
You can learn more about vuex here https://vuex.vuejs.org/
itemsMdCount:[],
getItemsCount()
{
window.axios.get(`/get-items-md-count/${this.model.id}`).then(response({
this:itemsMdCount = response.data.itemsMdCount
}));
},

Send data from model signal post_save to view

I am connected to an API then I save all data coming to my DB, I have already setup the signals for that model's post_save.
How can I display all new data to my feed without the users needing to reload the page ?
I created a scheduler using apscheduler that pulls out the data from the API every specific time.
updater.py
from datetime import datetime
from apscheduler.schedulers.background import BackgroundScheduler
from news_updater import newsAPI
def start():
print('sched start')
scheduler = BackgroundScheduler()
scheduler.add_job(newsAPI.get_fxstreet_news, 'interval', minutes=1)
scheduler.start()
apps.py
from django.apps import AppConfig
class NewsFilterConfig(AppConfig):
name = 'news_filter'
def ready(self):
from news_updater import updater
updater.start()
and I added this to my models.py
from django.db.models.signals import post_save, pre_save
def save_article(sender, instance, **kwargs):
print('new article saved')
post_save.connect(save_article, sender=NewsArticles)
it's already printing the 'new article saved' everytime a new data comes in.
I also have setup a channel and is connected but I don't know how I can piece everything together
consumers.py
import asyncio
import json
from channels.consumer import AsyncConsumer
from channels.db import database_sync_to_async
from .models import NewsArticles
class NewsArticlesConsumer(AsyncConsumer):
async def websocket_connect(self, event):
print('connected', event)
await self.send({
'type': 'websocket.accept'
})
latest_news_obj = await self.get_latest_news()
print(latest_news_obj)
await self.send({
'type': 'websocket.send',
'text': "hello world"
})
async def websocket_receive(self, event):
print('received', event)
async def websocket_disconnect(self, event):
print('disconnected', event)
#database_sync_to_async
def get_latest_news(self):
return NewsArticles.objects.filter(is_new=True)[0]

How to call a function in view by clicking a button in django?

I am trying to call the function ssl_verify from my html template . But it gives 404 error. Can anyone help me with this? Where i am wrong ?
#views.py
def ssl_verify( request , dns, port ):
if request.is_ajax():
result = dns + port
return result
#urls.py
url(r'ssl_verify/(\d+)/(\d+)/$', views.ssl_verify,name='ssl_verify'),
#script in html
function verify()
{
dns = document.getElementById("dns1").value;
port = document.getElementById("port1").value;
$.post('ssl_verify/'+dns+'/'+port+'/', function (data) {
alert (data) ;
});
}
Your urls.py must contain (replace the regexp line)
url(r'^ssl_verify/(?P<dns>[^/]+)/(?P<port>[^/]+)/$','views.check_ssl'),
or if you import:
from views import check_ssl
....
url(r'^ssl_verify/(?P<dns>[^/]+)/(?P<port>[^/]+)/$','check_ssl'),
and your views:
from django.http import HttpResponse
def check_ssl( request , dns, port ):
if request.is_ajax():
message = str(dns)+str(port)
return HttpResponse(message)
else:
return HttpResponse('/faulthandler') # declare in urls if needed

I tried to get title from this site (http://www.itslaw.com), it was loading by JavaScript

Here is my code, I using Python to get information, I use proxies, headers, session to simulate, but I kept getting 501.
# -*- coding: utf-8 -*-
import requests
from pyquery import PyQuery as pq
from goose import Goose
from goose.text import StopWordsChinese
import json
import time
class ItSlaw(object):
def __init__(self):
self.url = 'XXXX'
self.headers = {'XXXX'}
self.result = None
self.keyword = None
self.session = requests.Session()
def reset(self, keyword):
self.keyword = keyword
self.result = None
def fetch(self):
url = self.url.format(keyword='self.keyword',keywordcopy='self.keyword')
res = []
time.sleep(3)
proxies = {"http": "14.111.148.1"}
r = self.session.get(url, proxies=proxies)
print r.status_code
completed_url = 'http://www.itslaw.com/' + 'url'
g = Goose({'stopwords_class': StopWordsChinese})
article = g.extract(url=completed_url)
content = article.cleaned_text
res.append()
self.result = res
return self.result
def get_result(self):
return self.result
You can do it using selenium:
Install selenium for Python using pip.
For Linux(Ubuntu/Debian) it looks:
sudo apt-get install python-pip
sudo pip install selenium
(!)You have to google how to do it for your OS
then just run this code
import unittest
from selenium import webdriver
class GetTitle(unittest.TestCase):
def setUp(self):
self.driver = webdriver.Firefox()
def test_get_title(self):
driver = self.driver
driver.get("http://www.itslaw.com/")
print "Title is: ", driver.title
def tearDown(self):
self.driver.close()
if __name__ == "__main__":
unittest.main()
>>> Title is: 无讼案例|无讼名片-打造中国最大的互联网律师名片、案例检索服务平台

Categories

Resources