如何在React-Node.js Web应用程序中传递令牌(数据)(从Node.js文件到React TSX文件) [英] How to Pass token(data) in react-Nodejs web application (from nodejs file to react tsx file)

查看:109
本文介绍了如何在React-Node.js Web应用程序中传递令牌(数据)(从Node.js文件到React TSX文件)的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在使用nodeJS和reactjs Web应用程序测试bot框架代码,该代码可以按预期工作,但是由于Bearer令牌位于reactjs中,因此它在浏览器的调试器工具中可见,因此我打算进行其余的调用以在nodejs端的server.js文件中获取令牌.当前,令牌生成发生在reactjs端,如下面的代码所示. 这是链接到建立的应用程序

I am testing a bot framework code using nodeJS and reactjs web application, the code works as expected however since the bearer token is in reactjs it is visible in the debugger tools from the browser, so i am planning to have the rest call to get the token in the server.js file in the nodejs side. Currently the token generation happens on the reactjs side as shown in the code below. This is the link to the application build up

declare var require: any
var React = require('react');
var ReactDOM = require('react-dom');
import ReactWebChat, { createDirectLine } from 'botframework-webchat';
import { Provider } from 'react-redux'
import { createStyleSet } from 'botframework-webchat';
import { getAccessToken } from './server';

export class Hello extends React.Component {
    constructor() {
        super();

        this.state = {
            directLine: null,
            styleSet: null,
            userName: null
        };
    }
    async componentDidMount() {
        var s = getAccessToken;
        var responseFromAuthCall = "";

        this.setState(() => ({
            directLine: createDirectLine({ token }),

        }));
    }
    render() {
        const {
            state: { data }
        } = this

        return (
            this.state.directLine ?
                <ReactWebChat
                    className="chat"
                    directLine={this.state.directLine}
                    styleSet={this.state.styleSet}
                />
                :
                <div>Connecting to bot&hellip;</div>
        );
    }
}
ReactDOM.render(<Hello />, document.getElementById('root'));

下面是nodejs端server.js文件的代码

Below is the code for the server.js file on the nodejs side

'use strict';
var path = require('path');
var express = require('express');
var reactredux = require('react-redux');

const https = require('https');
var Request = require("request");
var app = express();
const axios = require('axios');
var staticPath = path.join(__dirname, '/');
app.use(express.static(staticPath));


exports.getAccessToken = function () {
    Request.post({
        "headers": { "Authorization": "Bearer token", 'Accept': 'application/json', 'Content-Type': 'application/json' },
        "url": "https://directline.botframework.com/v3/directline/tokens/generate",
        "body": JSON.stringify({
            "accessLevel": "View",
            "allowSaveAs": "false"
        })
    }, (error, response, body) => {
        if (error) {
            return console.dir(error);
        }
        return JSON.parse(body);
        //console.dir(JSON.parse(body));
        //console.log("test");
    });
};

var server = app.listen(app.get('port'), function () {
    console.log('listening');
});


// Allows you to set port in the project properties.    
app.set('port', process.env.PORT || 3000);

我正在导出getAccessToken函数并在reactjs端导入相同的函数,但是我在reatjs文件中导入它的方式似乎有问题....有什么建议吗?

I am exporting the getAccessToken function and importing the same in the reactjs side, but seems like there is some issue with the way i am importing it in the reatjs file....any suggestions?

Error:


C:\Users\loc>node_modules\.bin\webpack app.tsx --config webpack-config.js
Hash: 86894ea9d43d1a2268fb
Version: webpack 4.23.1
Time: 11781ms
Built at: 2019-06-24 16:10:48
              Asset      Size  Chunks             Chunk Names
    ./app-bundle.js  9.55 MiB    main  [emitted]  main
./app-bundle.js.map   9.7 MiB    main  [emitted]  main
Entrypoint main = ./app-bundle.js ./app-bundle.js.map
 [0] util (ignored) 15 bytes {main} [built]
 [1] util (ignored) 15 bytes {main} [built]
 [2] buffer (ignored) 15 bytes {main} [optional] [built]
 [3] crypto (ignored) 15 bytes {main} [optional] [built]
 [4] readable-stream (ignored) 15 bytes {main} [built]
 [5] supports-color (ignored) 15 bytes {main} [built]
 [6] chalk (ignored) 15 bytes {main} [built]
 [7] ./terminal-highlight (ignored) 15 bytes {main} [built]
[11] http (ignored) 15 bytes {main} [built]
 [./app.tsx] 9.15 KiB {main} [built]
 [./node_modules/express/lib sync recursive] ./node_modules/express/lib sync 160 bytes {main} [built]
 [./node_modules/webpack/buildin/global.js] (webpack)/buildin/global.js 489 bytes {main} [built]
 [./node_modules/webpack/buildin/harmony-module.js] (webpack)/buildin/harmony-module.js 573 bytes {main} [built]
 [./node_modules/webpack/buildin/module.js] (webpack)/buildin/module.js 497 bytes {main} [built]
 [./server.js] 3.59 KiB {main} [built]
    + 1277 hidden modules

WARNING in ./node_modules/express/lib/view.js 81:13-25
Critical dependency: the request of a dependency is an expression
 @ ./node_modules/express/lib/application.js
 @ ./node_modules/express/lib/express.js
 @ ./node_modules/express/index.js
 @ ./server.js
 @ ./app.tsx

WARNING in C:/Users/loc/node_modules/ajv/lib/async.js 96:20-33
Critical dependency: the request of a dependency is an expression
 @ C:/Users/loc/node_modules/ajv/lib/ajv.js
 @ C:/Users/loc/node_modules/har-validator/lib/node4/promise.js
 @ C:/Users/loc/node_modules/request/lib/har.js
 @ C:/Users/loc/node_modules/request/request.js
 @ C:/Users/loc/node_modules/request/index.js
 @ ./server.js
 @ ./app.tsx

WARNING in C:/Users/loc/node_modules/ajv/lib/async.js 119:15-28
Critical dependency: the request of a dependency is an expression
 @ C:/Users/loc/node_modules/ajv/lib/ajv.js
 @ C:/Users/loc/node_modules/har-validator/lib/node4/promise.js
 @ C:/Users/loc/node_modules/request/lib/har.js
 @ C:/Users/loc/node_modules/request/request.js
 @ C:/Users/loc/node_modules/request/index.js
 @ ./server.js
 @ ./app.tsx

WARNING in C:/Users/loc/node_modules/ajv/lib/compile/index.js 13:21-34
Critical dependency: the request of a dependency is an expression
 @ C:/Users/loc/node_modules/ajv/lib/ajv.js
 @ C:/Users/loc/node_modules/har-validator/lib/node4/promise.js
 @ C:/Users/loc/node_modules/request/lib/har.js
 @ C:/Users/loc/node_modules/request/request.js
 @ C:/Users/loc/node_modules/request/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in ./node_modules/destroy/index.js
Module not found: Error: Can't resolve 'fs' in 'C:\Users\loc\node_modules\destroy'
 @ ./node_modules/destroy/index.js 14:17-30
 @ ./node_modules/send/index.js
 @ ./node_modules/express/lib/utils.js
 @ ./node_modules/express/lib/application.js
 @ ./node_modules/express/lib/express.js
 @ ./node_modules/express/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in ./node_modules/etag/index.js
Module not found: Error: Can't resolve 'fs' in 'C:\Users\loc\node_modules\etag'
 @ ./node_modules/etag/index.js 22:12-25
 @ ./node_modules/express/lib/utils.js
 @ ./node_modules/express/lib/application.js
 @ ./node_modules/express/lib/express.js
 @ ./node_modules/express/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in ./node_modules/express/lib/view.js
Module not found: Error: Can't resolve 'fs' in 'C:\Users\loc\node_modules\express\lib'
 @ ./node_modules/express/lib/view.js 18:9-22
 @ ./node_modules/express/lib/application.js
 @ ./node_modules/express/lib/express.js
 @ ./node_modules/express/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in ./node_modules/mime/mime.js
Module not found: Error: Can't resolve 'fs' in 'C:\Users\loc\node_modules\mime'
 @ ./node_modules/mime/mime.js 2:9-22
 @ ./node_modules/send/index.js
 @ ./node_modules/express/lib/utils.js
 @ ./node_modules/express/lib/application.js
 @ ./node_modules/express/lib/express.js
 @ ./node_modules/express/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in ./node_modules/send/index.js
Module not found: Error: Can't resolve 'fs' in 'C:\Users\loc\node_modules\send'
 @ ./node_modules/send/index.js 23:9-22
 @ ./node_modules/express/lib/utils.js
 @ ./node_modules/express/lib/application.js
 @ ./node_modules/express/lib/express.js
 @ ./node_modules/express/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in C:/Users/loc/node_modules/request/lib/har.js
Module not found: Error: Can't resolve 'fs' in 'C:\Users\loc\node_modules\request\lib'
 @ C:/Users/loc/node_modules/request/lib/har.js 3:9-22
 @ C:/Users/loc/node_modules/request/request.js
 @ C:/Users/loc/node_modules/request/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in ./node_modules/express/lib/request.js
Module not found: Error: Can't resolve 'net' in 'C:\Users\loc\node_modules\express\lib'
 @ ./node_modules/express/lib/request.js 18:11-25
 @ ./node_modules/express/lib/express.js
 @ ./node_modules/express/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in C:/Users/loc/node_modules/forever-agent/index.js
Module not found: Error: Can't resolve 'net' in 'C:\Users\loc\node_modules\forever-agent'
 @ C:/Users/loc/node_modules/forever-agent/index.js 6:10-24
 @ C:/Users/loc/node_modules/request/request.js
 @ C:/Users/loc/node_modules/request/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in C:/Users/loc/node_modules/tough-cookie/lib/cookie.js
Module not found: Error: Can't resolve 'net' in 'C:\Users\loc\node_modules\tough-cookie\lib'
 @ C:/Users/loc/node_modules/tough-cookie/lib/cookie.js 32:10-24
 @ C:/Users/loc/node_modules/request/lib/cookies.js
 @ C:/Users/loc/node_modules/request/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in C:/Users/loc/node_modules/tunnel-agent/index.js
Module not found: Error: Can't resolve 'net' in 'C:\Users\loc\node_modules\tunnel-agent'
 @ C:/Users/loc/node_modules/tunnel-agent/index.js 3:10-24
 @ C:/Users/loc/node_modules/request/lib/tunnel.js
 @ C:/Users/loc/node_modules/request/request.js
 @ C:/Users/loc/node_modules/request/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in C:/Users/loc/node_modules/forever-agent/index.js
Module not found: Error: Can't resolve 'tls' in 'C:\Users\loc\node_modules\forever-agent'
 @ C:/Users/loc/node_modules/forever-agent/index.js 7:10-24
 @ C:/Users/loc/node_modules/request/request.js
 @ C:/Users/loc/node_modules/request/index.js
 @ ./server.js
 @ ./app.tsx

ERROR in C:/Users/loc/node_modules/tunnel-agent/index.js
Module not found: Error: Can't resolve 'tls' in 'C:\Users\loc\node_modules\tunnel-agent'
 @ C:/Users/loc/node_modules/tunnel-agent/index.js 4:10-24
 @ C:/Users/loc/node_modules/request/lib/tunnel.js
 @ C:/Users/loc/node_modules/request/request.js
 @ C:/Users/loc/node_modules/request/index.js
 @ ./server.js
 @ ./app.tsx

推荐答案

这就是我具有类似项目设置的方式,效果很好.

This is how I have a similar project setup which works quite well.

首先,将生成令牌的端点添加到您的机器人的index.js文件中.以下代码可以直接添加到文件末尾,也可以根据您的选择进行组织.当您的漫游器运行时,此端点也将可用.

First, add the token generating endpoint into you bot's index.js file. The following code can be appended directly to the end of the file or you can organize however you choose. While your bot is running, this endpoint will also be available.

可以,当然,可以在其他地方设置端点.它实际上可以在任何地方.我最初将以下内容放在一个单独的项目中,首先在Azure上,然后在本地与我的React项目并排运行,但是意识到我可以在bot中运行它.重要的部分是获取令牌(请参见下文).

You can, of course, setup your endpoint elsewhere. It literally can be anywhere. I originally had the below in a separate project, first on Azure, then locally running side-by-side with my React project but realized I could just run it in the bot. The important part is fetching the token (see further below).

在这种情况下,我在.env文件中有直接线路机密(process.env.directLineSecret).我也在3500端口(fyi)上运行它.

In this instance, I have the direct line secret (process.env.directLineSecret) in a .env file. I am also running it on port 3500 (fyi).

/**
 * Creates token server
 */
const bodyParser = require('body-parser');
const request = require('request');
const corsMiddleware = require('restify-cors-middleware');

const cors = corsMiddleware({
  origins: ['*']
});

// Create HTTP tokenServer.
let tokenServer = restify.createServer();
tokenServer.pre(cors.preflight);
tokenServer.use(cors.actual);
tokenServer.use(bodyParser.json({
  extended: false
}));
tokenServer.dl_name = 'DirectLine';
tokenServer.listen(process.env.port || process.env.PORT || 3500, function() {
  console.log(`\n${ tokenServer.dl_name } listening to ${ tokenServer.url }.`);
});

// Listen for incoming requests.
tokenServer.post('/directline/token', (req, res) => {
  // userId must start with `dl_`
  const userId = (req.body && req.body.id) ? req.body.id : `dl_${ Date.now() + Math.random().toString(36) }`;
  const options = {
    method: 'POST',
    uri: 'https://directline.botframework.com/v3/directline/tokens/generate',
    headers: {
      'Authorization': `Bearer ${ process.env.directLineSecret }`
    },
    json: {
      User: {
        Id: userId
      }
    }
  };
  request.post(options, (error, response, body) => {
    if (!error && response.statusCode < 300) {
      res.send({
        token: body.token
      });
    } else {
      res.status(500);
      res.send('Call to retrieve token from DirectLine failed');
    }
  });
});

接下来,创建您的WebChat组件.在这里,您将进行呼叫以获取令牌.确保使用与您的漫游器的index.js文件中指定的相同的端点/端口(或您创建的任何端点).该令牌将通过componentDidMount()与页面一起生成. directLine连接设置将保存为状态,并随后通过render()方法开始Web聊天会话时访问.

Next, create your WebChat component. Here you will make your call to get the token. Be sure to use the same endpoint / port you specified in your bot's index.js file (or whatever endpoint you created). The token will generate with the page via componentDidMount(). The directLine connection settings will be saved to state and, subsequently, accessed when the Web Chat session begins via the render() method.

import React from 'react';
import ReactWebChat, { createDirectLine } from 'botframework-webchat';

export default class WebChat extends React.Component {
  constructor(props) {
    super(props);

  componentDidMount() {
    this.fetchToken();
  }

  async fetchToken() {
    const res = await fetch( 'http://localhost:3500/directline/token', { method: 'POST' } );
    const { token } = await res.json();

    this.setState(() => ({
      directLine: createDirectLine({ token })
    }));
  }

  render() {
    return (
      this.state.directLine ?
          <ReactWebChat
            directLine={ this.state.directLine }
            styleSet={ this.state.styleSet }
            tableIndex="-1"
            { ...this.props }
          >
          </ReactWebChat>
      :
        <div>Connecting to bot&hellip;</div>
    )
  }
}

最后,我将机器人嵌入为一个单独的组件.我正在做一些其他的事情,这些事情我已经从这段代码中删除了,因此您可以将WebChat直接传递到您的App类中,也可以将其放置在任何地方.

Lastly, I have the bot embedded as a separate component. I'm doing some other stuff which I've cut out of this code, so you can likely pass WebChat directly into your App class or wherever you are planting it.

import React, { Component } from 'react';
import WebChat from './webchat';

class WebChatView extends Component {
  render() {
    return (
      <div>
        <WebChat id="webchat" role="main" />
      </div>
    )
  }
}

我对此进行了细化,为您简化了操作.如果某些方法不起作用,请告诉我,我将再次进行讨论.否则,您应该会很好.

I hacked bits out of this to simplify it for you. If something doesn't work, let me know and I'll revisit it. Otherwise, you should be good to go.

希望有帮助!

这篇关于如何在React-Node.js Web应用程序中传递令牌(数据)(从Node.js文件到React TSX文件)的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆