如何在React-Node.js Web应用程序中传递令牌(数据)(从Node.js文件到React TSX文件)

时间:2019-06-24 20:22:48

标签: node.js reactjs web-applications botframework

我正在使用nodeJS和reactjs Web应用程序测试bot框架代码,该代码可以按预期工作,但是由于承载令牌位于reactjs中,因此它在浏览器的调试器工具中可见,因此我打算进行其余的调用在nodejs端的server.js文件中获取令牌。当前,令牌生成发生在reactjs端,如下面的代码所示。 这是建立应用程序的https://streamsets.com/blog/replicating-oracle-mysql-json#ora-01291-missing-logfile

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文件的代码

'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文件中导入它的方式似乎存在问题。...有什么建议吗?

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

1 个答案:

答案 0 :(得分:2)

这就是我有一个类似的项目设置的方式,效果很好。

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

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

在这种情况下,我在.env文件中有直接密码(process.env.directLineSecret)。我也在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聊天会话时访问。

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类中或在您放置它的任何地方。

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

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

我从中删除了一些内容,以简化您的操作。如果某些方法不起作用,请告诉我,我将再次进行讨论。否则,您应该会很好。

希望有帮助!