sails.js从控制器方法访问控制器方法

时间:2013-12-22 23:55:22

标签: javascript node.js sails.js controllers

为什么你不能从另一个控制器方法中访问其他控制器方法?

像这样。

module.exports = 

   findStore: ->
       # do somthing

   index: ->
      @findStore(); # Error: undefined

编译

module.exports = {
  findStore: function() {},
  index: function() {
    return this.findStore(); // Error: undefined
  }
};

如果你不能这样做,为什么不呢?我怎么能这样做......

7 个答案:

答案 0 :(得分:64)

您可以使用sails.controllers.yourControllerName.findStore()

sails全局对象几乎引用了所有内容。

答案 1 :(得分:24)

在Sails中组织代码的最佳方法之一,至少对我和我的团队来说,一直是在服务(/ api / services)中拥有所有真正的业务逻辑。可以从任何控制器全局访问这些对象。

此外,一个好的做法是使用服务中的promise(因为Sails在模型方法中使用它们)

使用您的代码创建商店服务(StoreService.js):

module.exports = {
  findStore: function(storeId) {
    // here you call your models, add object security validation, etc...
    return Store.findOne(storeId);
  }
};

您的控制器应处理与请求,呼叫服务和返回适当响应相关的所有内容。

例如,在您的示例中,控制器可以具有:

module.exports = {
  index: function(req, res) {
    if(req.param('id')) {
      StoreService.findStore(req.param('id'))
        .then(res.ok)
        .catch(res.serverError);
    } else {
      res.badRequest('Missing Store id');
    }
  },
  findStore: function(req, res) {
    if(req.param('id')) {
      StoreService.findStore(req.param('id'))
        .then(res.ok)
        .catch(res.serverError);
    } else {
      res.badRequest('Missing Store id');
    }
  },
};

这样,您就拥有了非常简单的控制器,所有业务逻辑都由服务管理。

答案 2 :(得分:7)

过去几个小时遇到同样的问题。我使用了api / services文件夹。 它可能不是您需要的,但它是一个选项。 这里有一个很好的解释。 What services would one add to the api/services folder in sails.js

答案 3 :(得分:2)

当您尝试快速构建某些内容时,这有点令人讨厌,但从长远来看,它会强制实施良好的代码组织实践(通过将所有业务逻辑推入控制器变得更加困难)。 / p>

答案 4 :(得分:1)

我想建议一个有效的解决方案但不是最好的方法。我们可以使用bind函数将上下文与调用源绑定,如下所示:

generateUrl出现在Controller A

 // App code
     GraphRequest request = GraphRequest.newMeRequest(
                                loginResult.getAccessToken(),
                                new GraphRequest.GraphJSONObjectCallback() {
                                    @Override
                                    public void onCompleted(final JSONObject object, GraphResponse response) {
                                        Log.v("LoginActivity", response.toString());
                                        try {

                                            if (isurl) {
                                                ShareDialog shareDialog = new ShareDialog(mActivity);
                                                if (ShareDialog.canShow(ShareLinkContent.class)) {
                                                    ShareLinkContent linkContent = new ShareLinkContent.Builder()
                                                            .setContentUrl(Uri.parse("https://play.google.com/store?hl=en"))
                                                            .setContentDescription(message).setContentUrl(imgBitmapUri)
                                                            .build();
                                                    shareDialog.show(linkContent);
                                                }

                                            } else {
                                                SharePhoto.Builder sharePhotoBuilder = new SharePhoto.Builder();
                                                if (bitmap == null) {

                                                    sharePhotoBuilder.setBitmap(bitmap);
                                                } else {
                                                    sharePhotoBuilder.setImageUrl(Uri.parse(imgBitmapPath));
                                                }
                                                sharePhotoBuilder.setUserGenerated(false);
                                                final SharePhoto gesturePhoto = sharePhotoBuilder.build();
                                                ShareOpenGraphObject shareOpenGraphObject = new ShareOpenGraphObject.Builder()
                                                        .putString("og:type", "favorite.share")
                                                        .putString("og:description", message)
                                                        .putPhotoArrayList("og:image", new ArrayList<SharePhoto>() {{
                                                    add(gesturePhoto);
                                                        }}).build();
                                                ShareOpenGraphAction action = new ShareOpenGraphAction.Builder()
                                                        .setActionType("favorite.share")
                                                        .putObject("favorite:share", shareOpenGraphObject)
                                                        .build();
                                                ShareOpenGraphContent content = new ShareOpenGraphContent.Builder()
                                                        .setPreviewPropertyName("favorite:share").setPreviewPropertyName("image")
                                                        .setAction(action)
                                                        .build();
                                                ShareDialog.show(mActivity, content);
`enter code here`                                     }


                                            }

                                        } catch (Exception e) {
                                            e.printStackTrace();
                                        }
                                    }
                                });
                        Bundle parameters = new Bundle();
                        parameters.putString("fields", "id,name,first_name, last_name, email,link");
                        request.setParameters(parameters);
                        request.executeAsync();

获取URL是Controller A中的另一种方法

function generateUrl(){
  return 'www.google.com';
}

我希望这有帮助!

答案 5 :(得分:0)

解决此问题的更优雅方法是在函数名称前使用关键字this

示例:

one: function() {
   console.log('First Function');
},

two: function() {
   // call the function one in the same controller
   this.one();
}

答案 6 :(得分:0)

您可以执行以下操作:

//ArticleController
module.exports = {
  findStore: async () => {
    return await findStoreFunc(req.param('id'));
  },
  index: async () => {
    ...
    return await findStoreFunc(id);
  }
};

const findStoreFunc = async (id) => {...}

并使用另一个控制器的功能:

const ArticleController = require('./ArticleController');
//CustomerController
module.exports = {
  index: async () => {
    ...
    let article = await ArticleController.findStore(id);
    ...
  }
};