Coder Social home page Coder Social logo

loopback-example-access-control's Introduction

loopback-example-access-control

⚠️ This LoopBack 3 example project is no longer maintained. Please refer to LoopBack 4 Examples instead. ⚠️

$ git clone https://github.com/strongloop/loopback-example-access-control
$ cd loopback-example-access-control
$ npm install
$ node .

In this example, we create "Startkicker" (a basic Kickstarter-like application) to demonstrate authentication and authorization mechanisms in LoopBack. The application consists of four types of users:

  • guest
  • owner
  • team member
  • administrator

Each user type has permission to perform tasks based on their role and the application's ACL (access control list) entries.

Prerequisites

Tutorials

Knowledge

Procedure

Create the application

Application information

  • Name: loopback-example-access-control
  • Directory to contain the project: loopback-example-access-control
$ lb app loopback-example-access-control
... # follow the prompts
$ cd loopback-example-access-control

Add the models

Model information

  • Name: user
    • Datasource: db (memory)
    • Base class: User
    • Expose via REST: No
    • Custom plural form: Leave blank
    • Properties
      • None
  • Name: team
    • Datasource: db (memory)
    • Base class: PersistedModel
    • Expose via REST: No
    • Custom plural form: Leave blank
    • Properties
      • ownerId
        • Number
        • Not required
      • memberId
        • Number
        • Required
  • Name: project
    • Datasource: db (memory)
    • Base class: PersistedModel
    • Expose via REST: Yes
    • Custom plural form: Leave blank
    • Properties
      • name
        • String
        • Not required
      • balance
        • Number
        • Not required

No properties are required for the user model because we inherit them from the built-in User model by specifying it as the base class.

$ lb model user
... # follow the prompts, repeat for `team` and `project`

Define the remote methods

Define three remote methods in project.js:

Create the model relations

Model relation information

  • user
    • has many
      • project
        • Property name for the relation: projects
        • Custom foreign key: ownerId
        • Require a through model: No
      • team
        • Property name for the relation: teams
        • Custom foreign key: ownerId
        • Require a through model: No
  • team
    • has many
      • user
        • Property name for the relation: members
        • Custom foreign key: memberId
        • Require a through model: No
  • project
    • belongs to
      • user
        • Property name for the relation: user
        • Custom foreign key: ownerId

Add model instances

Create a boot script named sample-models.js.

This script does the following:

Configure server-side views

LoopBack comes preconfigured with EJS out-of-box. This means we can use server-side templating by simply setting the proper view engine and a directory to store the views.

Create a views directory to store server-side templates.

$ mkdir server/views

Create index.ejs in the views directory.

Configure server.js to use server-side templating. Remember to import the path package.

Add routes

Create routes.js. This script does the following:

When you log in sucessfully, projects.html is rendered with the authenticated user's access token embedded into each link.

Create the views

Create the views directory to store views.

In this directory, create index.ejs and projects.ejs.

Create a role resolver

Create role-resolver.js.

This file checks if the context relates to the project model and if the request maps to a user. If these two requirements are not met, the request is denied. Otherwise, we check to see if the user is a team member and process the request accordingly.

Create ACL entries

ACLs are used to restrict access to application REST endpoints.

ACL information

  • Deny access to all project REST endpoints
    • Select the model to apply the ACL entry to: (all existing models)
    • Select the ACL scope: All methods and properties
    • Select the access type: All (match all types)
    • Select the role: All users
    • Select the permission to apply: Explicitly deny access
  • Allow unrestricted access to GET /api/projects/listProjects
    • Select the model to apply the ACL entry to: project
    • Select the ACL scope: A single method
    • Enter the method name: listProjects
    • Select the role: All users
    • Select the permission to apply: Explicitly grant access
  • Only allow admin unrestricted access to GET /api/projects
    • Select the model to apply the ACL entry to: project
    • Select the ACL scope: A single method
    • Enter the method name: find
    • Select the role: other
    • Enter the role name: admin
    • Select the permission to apply: Explicitly grant access
  • Only allow team members access to GET /api/projects/:id
    • Select the model to apply the ACL entry to: project
    • Select the ACL scope: A single method
    • Enter the method name: findById
    • Select the role: other
    • Enter the role name: teamMember
    • Select the permission to apply: Explicitly grant access
  • Allow authenticated users to access POST /api/projects/donate
    • Select the model to apply the ACL entry to: project
    • Select the ACL scope: A single method
    • Enter the method name: donate
    • Select the role: Any authenticated user
    • Select the permission to apply: Explicitly grant access
  • Allow owners access to POST /api/projects/withdraw
    • Select the model to apply the ACL entry to: project
    • Select the ACL scope: A single method
    • Enter the method name: withdraw
    • Select the role: The user owning the object
    • Select the permission to apply: Explicitly grant access
$ lb acl
# follow the prompts, repeat for each ACL listed above

Try the application

Start the server (node .) and open localhost:3000 in your browser to view the app. You will see logins and explanations related to each user type we created:

  • Guest Guest
    • Role = $everyone, $unauthenticated
    • Has access to the "List projects" function, but none of the others
  • John Project owner
    • Role = $everyone, $authenticated, teamMember, $owner
    • Can access all functions except "View all projects"
  • Jane Project team member
    • Role = $everyone, $authenticated, teamMember
    • Can access all functions except "View all projects" and "Withdraw"
  • Bob Administrator
    • Role = $everyone, $authenticated, admin
    • Can access all functions except "Withdraw"

More LoopBack examples

loopback-example-access-control's People

Contributors

0candy avatar agnes512 avatar amir-61 avatar b-admike avatar bajtos avatar brunokindt avatar cgole avatar chertpong avatar crandmck avatar csakis avatar cspinillo avatar deniselee avatar deslee avatar dhmlau avatar jbeurel avatar luckylooke avatar manishbalodia avatar manojchandrashekar avatar raymondfeng avatar richardpringle avatar rmg avatar sam-github avatar sequoia avatar siddhipai avatar simonhoibm avatar smartmouse avatar superkhau avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

loopback-example-access-control's Issues

cookies for authentication : possible in this example?

Is the use of cookies for authentication (instead of tokens) possible in this example or do I something else in order to support cookies?

http://docs.strongloop.com/display/public/LB/Making+authenticated+requests
indicates:that the use of cookies can be enabled with:
app.use(loopback.token({ model: app.models.accessToken })); // before boot ie boot(app, __dirname);

I have used the suggested line, but cannot see any change in the post ?access_token (still there) or find a cookie.

role-resolver.js

Either it is a bug or I do not understand well.

https://github.com/strongloop/loopback-example-access-control/blob/master/server/boot/role-resolver.js

Line 23: context.model.findById(context.modelId, function(err, project) {

context here is project. So modelId is Id of the project model or what exactly is that?

What I understand is

  1. Check context.modelName is project or not
  2. check user is authenticated by checking context.accessToken.userId
  3. Then Look for project by id of project or something else ?

And why context.modelId is and always 1 ? I use mongodb so it should be string of ObjectId.

How to override models and their ACL?

I have setup the example with success.

PB :

Now, I want to give only to the admin role to create "users"

1- Solution 1 : Copy the "User" Loopback model in common/models/ and I change it as I want. Then I configure a Grunt task that copy it again to the loopback/models/

2- Solution 2 : I use "user" model that inherit the "User" LoopBack model. I add the following ACL
{
"principalType": "ROLE",
"principalId": "$everyone",
"permission": "DENY",
"property": "create"
}
Now my problem is : I can't create a "user" but I can create a "User".

Question :

How can I override the default model of "User" (properties, method, relations, ACL...) without copying it in my application?
expl :
user model :
{
"name":"User",
"override/mix": true
}

Thx

Question: Why `User` model is configured along with `user`?

In server/model-config.json we can see:

...
  "User": {
    "dataSource": "db"
  },
  "AccessToken": {
    "dataSource": "db",
    "public": false
  },
  "ACL": {
    "dataSource": "db",
    "public": false
  },
  "RoleMapping": {
    "dataSource": "db",
    "public": false
  },
  "Role": {
    "dataSource": "db",
    "public": false
  },
  "user": {
    "dataSource": "db",
    "public": true
  }
...

, where User seems to be redundant. Is there a hidden / obscure purpose it stands for?

Provisioning Logout

I can't seem to find how the 'User.login()' method is successful. I'm working on my own project where i'm trying to connect through Angular, and into my Strongloop User model. When trying to execute the 'User.logout()' method, I keep getting a 400 error.

Any suggestions on what I should modify in the code base?

Error: Cannot GET /cordova.js

I merged the code in folder client to strongloop/loopback-example-extendedAPI/client, the server was started successfully, but I click login button, the server is crush and the below exception was throw:

Error: Cannot GET /cordova.js
    at raiseUrlNotFoundError (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/lib/middleware/urlNotFound.js:15:17)
    at Layer.handle [as handle_request] (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/layer.js:76:5)
    at trim_prefix (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:263:13)
    at /Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:230:9
    at Function.proto.process_params (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:305:12)
    at /Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:221:12
    at Function.match_layer (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:288:3)
    at next (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:182:10)
    at SendStream.error (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/node_modules/serve-static/index.js:91:7)
    at SendStream.emit (events.js:95:17)
Error: Cannot GET /cordova.js
    at raiseUrlNotFoundError (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/lib/middleware/urlNotFound.js:15:17)
    at Layer.handle [as handle_request] (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/layer.js:76:5)
    at trim_prefix (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:263:13)
    at /Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:230:9
    at Function.proto.process_params (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:305:12)
    at /Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:221:12
    at Function.match_layer (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:288:3)
    at next (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/lib/router/index.js:182:10)
    at SendStream.error (/Users/happysky/Documents/cupid/CuipdRest/node_modules/loopback/node_modules/express/node_modules/serve-static/index.js:91:7)
    at SendStream.emit (events.js:95:17)

[optional dependency "strong-agent" module not found] while running loopback-access-control

Error:

C:\Users\RG\Desktop\node\loopback-example-access-control\server>slc run
strong-agent not profiling, configuration not found.
Generate configuration with:
    npm install -g strong-cli
    slc strongops
See http://docs.strongloop.com/strong-agent for more information.
supervisor running without clustering (unsupervised)
Could not load operational dependencies:
{ [Error: Cannot find module 'strong-agent'] code: 'MODULE_NOT_FOUND' }

C:\Users\RG\Desktop\node\loopback-example-access-control\server\app.js:17
if(clusterOptions.clustered && clusterOptions.isMaster) {
                 ^
TypeError: Cannot read property 'clustered' of undefined
    at Object.<anonymous> (C:\Users\RG\Desktop\node\loopback-example-access-cont
rol\server\app.js:17:18)
    at Module._compile (module.js:456:26)
    at Object.Module._extensions..js (module.js:474:10)
    at Module.load (module.js:356:32)
    at Function.Module._load (module.js:312:12)
    at Object.<anonymous> (C:\Users\RG\AppData\Roaming\npm\node_modules\strong-s
upervisor\bin\slr:27:19)
    at Module._compile (module.js:456:26)
    at Object.Module._extensions..js (module.js:474:10)
    at Module.load (module.js:356:32)
    at Function.Module._load (module.js:312:12)

PS : I have just started learning it, so if there is some mistake in my part, please specify it

/users/:id/account not accessible

Hi,

I'm trying to wrap my head around loopback's ACL but I couldn't figure out why /users/:id/account is not accessible even when logged in user calls it. Keeps getting access denied.

/accounts/:id?access_token=<token> also got access denied.

I thought since user belongs to account and account has acl:


{
          "accessType": "*",
          "permission": "ALLOW",
          "principalType": "ROLE",
          "principalId": "$owner"
}

account can be accessed by the owner which is the user it is associated with.

Enlighten me, please 😄

Cannot find module 'body-parser'

trying to do the tutorial manually and getting the same error even if i download the master:

C:\Projects\StrongLoop\loopback-example-access-control-master>slc run
INFO strong-agent API key not found, StrongOps dashboard reporting disabled.
Generate configuration with:
npm install -g strongloop
slc strongops
See http://docs.strongloop.com/strong-agent for more information.
supervisor running without clustering (unsupervised)

module.js:340
throw err;
^
Error: Cannot find module 'body-parser'
at Function.Module._resolveFilename (module.js:338:15)
at Function.Module._load (module.js:280:25)
at Module.require (module.js:364:17)
at require (module.js:380:17)
at Object. (C:\Projects\StrongLoop\loopback-example-access-control-master\server\serv
er.js:1:80)
at Module._compile (module.js:456:26)
at Object.Module._extensions..js (module.js:474:10)
at Module.load (module.js:356:32)
at Function.Module._load (module.js:312:12)
at Object. (C:\Users\nbdn7o6\AppData\Roaming\npm\node_modules\strongloop\node_modules
\strong-supervisor\bin\sl-run.js:40:19)

Trouble accessing boot-script generated users via API

I'm still new to Loopback so excuse this potentially dumb question.

When I boot the server I see in the command line:

$ slc run
Browse your REST API at http://0.0.0.0:3000/explorer
Web server listening at: http://0.0.0.0:3000/
Created users: [ { username: 'John',
    email: '[email protected]',
    password: '$2a$10$WZaZVACDLA6XgfRFTdcag.jncoZ32mXWjHf0I8qzowFGPaAauFmc.',
    id: 1 },
  { username: 'Jane',
    email: '[email protected]',
    password: '$2a$10$87Ra09lCIE0K0pR/pkSx2OjarfWnyr3n2ZPthoyg23xNsezNEOeUe',
    id: 2 },
  { username: 'Bob',
    email: '[email protected]',
    password: '$2a$10$zZHcGxcNjoQ8mhd/O4cuZeft1ePPC.Nep462EJs.00D78p94TgaWa',
    id: 3 } ]
...

However, when I try and use the API to GET the users:

http://0.0.0.0:3000/api/users

I get an empty response:

[]

I tried changing the data connector to use Mongo and I noticed that both a "Users" and "users" collection are made. The API seems to always go to the "User" collection (even POST) even though the accounts created in the boot script are in the "users" collection as User.create() goes to that collection.

I have also posed this question on the Loopback Google Group but am still awaiting reply.

https://groups.google.com/forum/#!topic/loopbackjs/Wc9Tdz4OsvM

Thanks for your time

What is the reason to duplicate REST API's find()? Is this some kind of LB's "best practices"?

I'm reading Access control concepts of Loopback (https://docs.strongloop.com/display/public/LB/Controlling+data+access). And I don't understand why they duplicate find().

Here is a text from docs:
controlling data access - loopback - documentation - google chrome 2015-11-07 20 04 54

That custom remote listProjects() method still uses default REST API's find() internally.

loopback-example-access-control_project js at master strongloop_loopback-example-access-control - google chrome 2015-11-07 20 18 29

So, what I see here is that admin is forced to use a default LB's REST API find(), and all other users are forced not to use LB's REST API, but only to use custom remote method listProjects(). Why?

Why do they close default REST API for all users? What genius idea is behind this approach? Is it some kind of LB's best practices to forbid to use default REST API for all users? Where can I read more about this?

Refactor `user` to another name

We get a lot of confusion from my original implementation of user extending builtin User. We should rename it to something like CustomUser or something to signify it's obviously not the same as builtin User.

the $q couldn't be invoked under the folder client

I was trying to invoke $q in my services.js under the folder client, but there is a excetpion in testing broswer page as below;but I did npm install q! Why was the program unable to run $q.defer()?

Uncaught Error: [$injector:modulerr] Failed to instantiate module starter due to:
Error: [$injector:modulerr] Failed to instantiate module starter.services due to:
Error: [$injector:nomod] Module 'starter.services' is not available! You either misspelled the module name or forgot to load it. If registering a module ensure that you specify the dependencies as the second argument.
http://errors.angularjs.org/1.2.3/$injector/nomod?p0=starter.services
at http://127.0.0.1:3000/js/bower_components/angular/angular.js:78:12
at http://127.0.0.1:3000/js/bower_components/angular/angular.js:1522:17
at ensure (http://127.0.0.1:3000/js/bower_components/angular/angular.js:1447:38)
at module (http://127.0.0.1:3000/js/bower_components/angular/angular.js:1520:14)
at http://127.0.0.1:3000/js/bower_components/angular/angular.js:3549:22
at Array.forEach (native)
at forEach (http://127.0.0.1:3000/js/bower_components/angular/angular.js:300:11)
at loadModules (http://127.0.0.1:3000/js/bower_components/angular/angular.js:3543:5)
at http://127.0.0.1:3000/js/bower_components/angular/angular.js:3550:40
at Array.forEach (native)
http://errors.angularjs.org/1.2.3/$injector/modulerr?p0=starter.services&p1…ngular%2Fangular.js%3A3550%3A40%0A%20%20%20%20at%20Array.forEach%20(native)
at http://127.0.0.1:3000/js/bower_components/angular/angular.js:78:12
at http://127.0.0.1:3000/js/bower_components/angular/angular.js:3577:15
at Array.forEach (native)
at forEach (http://127.0.0.1:3000/js/bower_components/angular/angular.js:300:11)
at loadModules (http://127.0.0.1:3000/js/bower_components/angular/angular.js:3543:5)
at http://127.0.0.1:3000/js/bower_components/angular/angular.js:3550:40
at Array.forEach (native)
at forEach (http://127.0.0.1:3000/js/bower_components/angular/angular.js:300:11)
at loadModules (http://127.0.0.1:3000/js/bower_components/angular/angular.js:3543:5)
at createInjector (http://127.0.0.1:3000/js/bower_components/angular/angular.js:3483:11)

Dynamic ACL and Other Principal Types

  • We need to showcase examples of access controls that apply to specific model instances (data).
  • We need to add some access controls that use other principal types (beyond ROLE).

@raymondfeng can you come up with some examples that would make sense for this repo example?

This is an excerpt from a comment you made in confluence a while back:

Use cases:
Authenticate client applications, users, and/or devices  to identify who (which  principals) are calling the APIs
Personalization (use the established principals to personalize the response)
Protection (check the established principals against access control lists to protect sensitive information)
Authorize access to protected resources against those who makes the request

Dump automigrate/autoupdate SQL commands

I found these below models were stored in database:
"user","accessToken","bank", "account" "transaction", "alert"
Would you like to share the SQL to create these tables for the models in database please?

Modifications to lb-services.js

I noticed that the loopback angular SDK generated code, lb-services.js, has some modifications to it(such as interceptors on some of the User methods).

I have my gruntfile set up so that lb-services.js gets re-generated every time. The app is in development and I'll be making changes to the models frequently so I re-generate lb-services.js in my grunt workflow.

Is there a way to take the modifications you have made to lb-services.js and put them in a different file? If this could be done in such a way that I can re-generate lb-services.js and still keep the functionality of the modifications you have on it, it would be a huge help.

If not, what is the right way of dealing with frequent changes in the model and needing to re-generate lb-services.js often? Do you have to manually merge in the changes in this example every time? Or is there a better way?

server shutdown when I try to login as non Guest (jane , jhon or bob )

bug trace as follow:

  token = token.toJSON();
                ^

TypeError: Cannot call method 'toJSON' of undefined
at C:\nodejsProjects\loopback-example-access-control\server\boot\routes.js:2
1:21
at C:\nodejsProjects\loopback-example-access-control\node_modules\loopback\c
ommon\models\user.js:219:9
at C:\nodejsProjects\loopback-example-access-control\node_modules\loopback-d
atasource-juggler\lib\dao.js:858:62
at C:\nodejsProjects\loopback-example-access-control\node_modules\loopback-d
atasource-juggler\lib\dao.js:834:7
at C:\nodejsProjects\loopback-example-access-control\node_modules\loopback-d
atasource-juggler\lib\connectors\memory.js:345:7
at C:\nodejsProjects\loopback-example-access-control\node_modules\loopback\n
ode_modules\continuation-local-storage\node_modules\async-listener\glue.js:188:3
1
at C:\nodejsProjects\loopback-example-access-control\node_modules\loopback\n
ode_modules\continuation-local-storage\node_modules\async-listener\glue.js:188:3
1
at process._tickDomainCallback (node.js:486:13)
at process. (C:\nodejsProjects\loopback-example-access-control\no
de_modules\loopback\node_modules\continuation-local-storage\node_modules\async-l
istener\index.js:18:15)

looopback_sdk_angular failed

I'm following this example http://docs.strongloop.com/display/LB/AngularJS+JavaScript+SDK to try to combine loopback.io and angularjs.

But when i create Gruntfile.js and then run grunt. It showed that task loopback_angular not found, so I open node_modules/grunt_loopback_sdk_angular/tasks/loopback_angular.js and find there is a task loopback_sdk_angular. So I changed task name in Gruntfile.js from loopback_angular to loopback_sdk_angular, and rerun grunt. It showed new error No "loopback_sdk_angular" targets found.

Please tell me how to fix it

How to shorten ACLs definitions ?

I have read below documents but i have problem need your help:
http://docs.strongloop.com/display/LB/Controlling+data+access
http://docs.strongloop.com/display/LB/Model+definition+JSON+file

  "acls": [
    {
      "principalType": "ROLE",
      "principalId": "$everyone",
      "permission": "DENY",
      "accessType": "*",
      "property": "*"
    },
    {
      "principalType": "ROLE",
      "principalId": "$unauthenticated ",
      "permission": "ALLOW",
      "accessType": "WRITE",
      "property": "create"
    },
    {
      "principalType": "ROLE",
      "principalId": "$unauthenticated ",
      "permission": "ALLOW",
      "accessType": "WRITE",
      "property": "login"
    },
    {
      "principalType": "ROLE",
      "principalId": "$unauthenticated ",
      "permission": "ALLOW",
      "accessType": "WRITE",
      "property": "confirm"
    },
    {
      "principalType": "ROLE",
      "principalId": "$unauthenticated ",
      "permission": "ALLOW",
      "accessType": "WRITE",
      "property": "reset"
    },
    {
      "principalType": "ROLE",
      "principalId": "$owner ",
      "permission": "ALLOW",
      "accessType": "*",
      "property": "*"
    }
  ],

It's too long, is there anyway to shorten it.
Can you help me write a tutorial for loopback 2.0
Thanks a lot.

Model resource is undefined

I'm trying to create a very simple create form for an organization. I managed to get the Loopback stuff working pretty easily and was able to wire up angular seed with it. I ran the Grunt task and included lbServices but no matter what I do, my resource is always undefined. See this gist.

ownerId is not in the roles

I'm trying to apply this example inside my project, and after one week looking for solutions, documents and examples I decided look inside role.js and found this:
#165: var ownerId = inst.userId || inst.owner;

So the "ownerId" in this example does not work because role.js just look for userId or owner field.

And the next step in line 173 that looks for relations does not work either, because I tried to use ownerId that should be matched in this point and it's fail.

Use ACL in non REST routes

Is it possible to figure out the users roles in a standard express route? For example, one might want to have a route accessible only for certain roles. How would this work?

AccessToken not being sent on subsequent requests after login

I'm getting the following on windows. Everything seemed to be ok except that when I went to write the authentication code I realized that the generated Angular factory was not passing the accesstoken with subsequent requests following the login. When comparing my code against the example application I noticed I'm missing the interceptor code for each endpoint method. I tried setting the public property for AccessToken to true in model-config.json which made the Warning go away, but the login method is still not passing the AccessToken along with subsequent requests. Any help is appreciated!

$ lb-ng ../server/server.js js/lb-services.js
Loading LoopBack app "e:\Google Drive\Development\Projects\Tribe Base\Minda\server\server.js"
Generating "lbServices" for the API endpoint "/api"
Warning: scope User.accessTokens targets class "AccessToken", which is not exposed
via remoting. The Angular code for this scope won't be generated.
Saving the generated services source to "e:\Google Drive\Development\Projects\Tribe Base\Minda\client\js\lb-services.js"

Here's my login method that was generated
"login": {
url: urlBase + "/Users/login",
method: "POST",
},

but I think it should look like this:

"login": {
url: urlBase + "/users/login",
method: "POST",
interceptor: {
response: function(response) {
var accessToken = response.data;
LoopBackAuth.currentUserId = accessToken.userId;
LoopBackAuth.accessTokenId = accessToken.id;
LoopBackAuth.rememberMe = response.config.params.rememberMe !== false;
LoopBackAuth.save();
return response.resource;
}
}
},

I was unable to get anythings after executed command git

I execute the command :sudo git clone [email protected]:strongloop/loopback-example-access-control.git. But , I was unable to get anythings as the output below:

sudo git clone [email protected]:strongloop/loopback-example-access-control.git
Password:
Cloning into 'loopback-example-access-control'...
Permission denied (publickey).
fatal: Could not read from remote repository.

Please make sure you have the correct access rights
and the repository exists.

Access control not enforced

I got the app up and running and then request the transactions from the test data user (1) using curl - so I am not passing a token, so I am not authenticated.
It happily returns all the transaction, which it shouldn't

$ curl http://0.0.0.0:4000/api/users/1/transactions
[
{
"id": 1,
"userId": 1,
"accountId": 1,
"pos": "Gas and Test",
"credit": 8283.81,
"time": "2013-01-12T13:52:23.826Z"
},
{
"id": 2,
"userId": 1,
"accountId": 1,
"pos": "Jasmine Tea",
"debit": 236.76,
"time": "2013-03-09T06:35:51.862Z"
},
...

Node app fails

I ran npm install ok and have a current slc version but when I cd to server and run node app I get this.

MacPro:server peterclough$ node app
connect deprecated multipart: use parser (multiparty, busboy, formidable) npm module instead node_modules/loopback/node_modules/express/node_modules/connect/lib/middleware/bodyParser.js:56:20
connect deprecated limit: Restrict request size at location of read node_modules/loopback/node_modules/express/node_modules/connect/lib/middleware/multipart.js:86:15
connect deprecated methodOverride: use method-override npm module instead app.js:23:18

events.js:72
        throw er; // Unhandled 'error' event
              ^
Error: listen EADDRINUSE
    at errnoException (net.js:904:11)
    at Server._listen2 (net.js:1042:14)
    at listen (net.js:1064:10)
    at net.js:1146:9
    at dns.js:72:18
    at process._tickDomainCallback (node.js:463:13)
    at Function.Module.runMain (module.js:499:11)
    at startup (node.js:119:16)
    at node.js:906:3
MacPro:server peterclough$ ls
app.js          datasources.json    models.json     package.json
app.json        models          node_modules        test
MacPro:server peterclough$ slc version
strong-cli v2.6.2 (node v0.10.29)
node-inspector v0.7.4
strong-build v0.1.2
strong-deploy v0.1.1
strong-pm v0.1.6
strong-registry v1.1.0
strong-supervisor v0.3.0 (strong-agent v0.4.12, strong-cluster-control v0.5.0)
generator-loopback v1.1.2
loopback-sdk-angular-cli v1.1.4
MacPro:server peterclough$ 

Any ideas?

slc does not support relation command

Your readme says that slc version >= 2.0.0 is required for these examples. I presently have v2.0.4 installed and it does not appear to support the relation command.

csalch@Chriss-MacBook-Air ~/code $ slc version
slc v2.0.4 (node v0.10.22)

csalch@Chriss-MacBook-Air ~/code $ slc lb relation person --has-many imageSet
connect.multipart() will be removed in connect 3.0
visit https://github.com/senchalabs/connect/wiki/Connect-3.0 for alternatives
connect.limit() will be removed in connect 3.0
relation is not a supported command
csalch@Chriss-MacBook-Air ~/code $

ROLE $owner not work

Hello,
I've try the example and make a new one like this, one user model have many device.
When i GET /devices with logged token, alway responsed with message "Authorization Required". But if i change principalId to "admin", it works.

user model

{
  "name": "user",
  "base": "User",
  "idInjection": true,
  "properties": {},
  "validations": [],
  "relations": {
    "devices": {
      "type": "hasMany",
      "model": "device",
      "foreignKey": "ownerId"
    }
  },
  "acls": [],
  "methods": []
}

device model

{
  "name": "device",
  "base": "PersistedModel",
  "idInjection": false,
  "properties": {
    "name": {
      "type": "string"
    },
    "devid": {
      "type": "string",
      "id": true
    },
    "online": {
      "type": "boolean",
      "default": false
    }
  },
  "validations": [],
  "relations": {
    "user": {
      "type": "belongsTo",
      "model": "user",
      "foreignKey": ""
    }
  },
  "acls": [
    {
      "accessType": "*",
      "principalType": "ROLE",
      "principalId": "$everyone",
      "permission": "DENY"
    },
    {
      "accessType": "*",
      "principalType": "ROLE",
      "principalId": "$owner",
      "permission": "ALLOW"
    }
  ],
  "methods": []
}

Debug message:

Fri, 23 Jan 2015 15:39:56 GMT express deprecated req.param(name): Use req.params, req.body, or req.query instead at node_modules/loopback/node_modules/strong-remoting/lib/http-context.js:142:18
Fri, 23 Jan 2015 15:39:56 GMT express deprecated req.param(name): Use req.params, req.body, or req.query instead at node_modules/loopback/node_modules/strong-remoting/lib/http-context.js:153:22
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:role isInRole(): $everyone
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context ---AccessContext---
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context principals:
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context principal: {"type":"USER","id":"54c26afcb48c2c0104398b29"}
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context modelName device
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context modelId undefined
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context property find
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context method find
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context accessType READ
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context accessToken:
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context   id "Suq9lKkS7iuCbUvyPkEdiWdrml6sANeBS3qKPAxcmwZqcpvUBXPo9IwYt2ncjQkT"
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context   ttl 1209600
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context getUserId() 54c26afcb48c2c0104398b29
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context isAuthenticated() true
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:role Custom resolver found for role $everyone
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:role isInRole(): $owner
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context ---AccessContext---
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context principals:
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context principal: {"type":"USER","id":"54c26afcb48c2c0104398b29"}
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context modelName device
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context modelId undefined
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context property find
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context method find
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context accessType READ
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context accessToken:
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context   id "Suq9lKkS7iuCbUvyPkEdiWdrml6sANeBS3qKPAxcmwZqcpvUBXPo9IwYt2ncjQkT"
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context   ttl 1209600
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context getUserId() 54c26afcb48c2c0104398b29
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context isAuthenticated() true
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:role Custom resolver found for role $owner
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl The following ACLs were searched: 
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl ---ACL---
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl model device
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl property *
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl principalType ROLE
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl principalId $everyone
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl accessType *
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl permission DENY
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl with score: 7495
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:acl ---Resolved---
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context ---AccessRequest---
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context  model device
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context  property find
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context  accessType READ
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context  permission DENY
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context  isWildcard() false
Fri, 23 Jan 2015 15:39:56 GMT loopback:security:access-context  isAllowed() false

ValidationError: The `team` instance is not valid. Details: `memberId` can't be blank (value: NaN)

Hi, i'm trying to use Mongodb as data source, but i get this error during sample creations:

Web server listening at: http://0.0.0.0:3000
Browse your REST API at http://0.0.0.0:3000/explorer
Created users: [ { username: 'John',
email: '[email protected]',
password: '$2a$10$eQQuWFROKW1SWFC1VjOBUOEWtq4Gu8aqqVXTa8RgWwB5AjCPGvRzO',
id: 56435f381fded18a4f15af6d },
{ username: 'Jane',
email: '[email protected]',
password: '$2a$10$r8Lffj2OPEp5W.clO0.HvOuXclbwOURRHDDOAdeyLR3BJhrWdpdNS',
id: 56435f381fded18a4f15af6e },
{ username: 'Bob',
email: '[email protected]',
password: '$2a$10$N/JyYFKX9/PO0cg9LjTmZOqmSTAJjy6UgEc6C13TmSpM.VxqNodqu',
id: 56435f381fded18a4f15af6c } ]
Created project: { name: 'project1',
balance: 100,
ownerId: 56435f381fded18a4f15af6d,
id: 56435f3a1fded18a4f15af6f }

/Users/melaporpora/working-sites/loopback-example-access-control/server/boot/sample-models.js:30
if (err) throw err;
^
ValidationError: The team instance is not valid. Details: memberId can't be blank (value: NaN).,ValidationError: The team instance is not valid. Details: memberId can't be blank (value: NaN).

Authentication problem in Loopback-example-access-control

I cloned a fresh copy of this repo remove unnecessary models and install npm dependencies then run the app. Now when I try

$curl -X POST -H "Content-Type:application/json" -d '{"email": "[email protected]", "password": "123456", "ttl": 1209600000}' http://0.0.0.0:3000/api/users/login

It returns me

{
  "id": "2prwjVaT7bjvNDFsVwDPqmGmAASPaLktgcyWLFia6GVp9L4SaQSID6Vj5qK2k0vF",
  "ttl": 31556926,
  "created": "2014-09-11T09:10:44.483Z",
  "userId": 1
}

Then I run the following commands

$ACCESS_TOKEN=2prwjVaT7bjvNDFsVwDPqmGmAASPaLktgcyWLFia6GVp9L4SaQSID6Vj5qK2k0vF
$curl -X GET -H "Authorization: $ACCESS_TOKEN" http://0.0.0.0:3000/api/users

It returns me this instead of returning the list of users

{  
  "error": {
"name": "Error",
"status": 401,
"message": "Authorization Required",
"statusCode": 401,
"stack":" …."
   }
}

Am I calling the api in right way? if yes then what is the problem. I followed this post
http://docs.strongloop.com/display/LB/Creating+and+authenticating+users
Thanks in Advance.
models.json

{
  "email": {
    "options": {
      "base": "Email",
      "acls": [
        {
          "accessType": "*",
          "permission": "DENY",
          "principalType": "ROLE",
          "principalId": "$everyone"
        }
      ]
    },
    "dataSource": "mail",
    "public": false
  },
  "user": {
    "options": {
      "base": "User",
      "relations": {
        "accessTokens": {
          "model": "accessToken",
          "type": "hasMany",
          "foreignKey": "userId"
        }
      },
      "acls": [
       {
          "principalType": "ROLE",
          "principalId": "$everyone",
          "permission": "ALLOW",
          "accessType": "*"
      }
      ]
    },
    "dataSource": "db",
    "public": true
  },
  "accessToken": {
    "options": {
      "base": "AccessToken",
      "baseUrl": "access-tokens",
      "acls": [
        {
          "accessType": "*",
          "permission": "DENY",
          "principalType": "ROLE",
          "principalId": "$everyone"
        },
        {
          "permission": "ALLOW",
          "principalType": "ROLE",
          "principalId": "$everyone",
          "property": "create"
        }
      ]
    },
    "dataSource": "db",
    "public": true
  }
}

User.count return a function in lb-services.js

I test the below code in controller,but the method User.count in lb-services.js returned a a function like the below shut-screen but not a number value.
------------------------------test js code in controller.js--------------------------------------

.controller('View1Ctrl', function($scope, User,Account,$location, AppAuth) {
   alert('controller.View1Ctrl.......1.1');
   AppAuth.ensureHasCurrentUser(User);
   $scope.currentUser = AppAuth.currentUser;
   alert('$scope.currentUser=======>'+$scope.currentUser.firstName.toString());
   $scope.account = User.count;
   // alert('$scope.account=======>'+$scope.account.toString());  
   // $scope.account = Account.count;  // Add LoopBack model
   alert('controller.View1Ctrl.......2');
   alert('$scope.account=======>'+$scope.account.toString());  
   // var next = $location.nextAfterLogin || '/';
   // alert('next=========>'+next);
   // // AppAuth.currentUser = $scope.loginResult.user;
   // // $location.path(next);
   // alert('controller.View1Ctrl.......over1');
})

anguar

role-resolver.js

Hi

Will like to know how does this role.resolver.js get called when accessing from
Show balance for project 1?
As I am looking to add more control on this role.

Regards

Testing dynamic roles

Hi everybody,

as per my understandings the Role.registerResolver callback is triggered only if someone try to access a route where this role is used in the Acl.

I'm wondering which is the best way to write test for dynamic roles, as now I found out two ways:

  • using loopback-testing to perform e2e test on protected routes
  • perform unit tests on the Role.registerResolver callback

Any suggestion?

Problem with the loopback-datasource-juggler version

npm install

npm ERR! peerinvalid The package loopback-datasource-juggler does not satisfy its siblings' peerDependencies requirements!
npm ERR! peerinvalid Peer [email protected] wants loopback-datasource-juggler@^1.4.0 < 1.6.0
npm ERR! peerinvalid Peer [email protected] wants [email protected]

npm ERR! System Linux 3.13.0-24-generic
npm ERR! command "/usr/bin/node" "/usr/bin/npm" "install"
npm ERR! cwd /home/lin/git/loopback-example-access-control/server
npm ERR! node -v v0.10.26
npm ERR! npm -v 1.4.3
npm ERR! code EPEERINVALID

how to remove/backout a relation?

While going through the tutorial I have incorrectly specified a name for the relation - should be "members" instead of "users".

  • How do I undo the above?

C:\Projects\StrongLoop\loopback-example-access-control>slc loopback:relation
? Select the model to create the relationship from: team
? Relation type: has many
? Choose a model to create a relationship with: user
? Enter the property name for the relation: users
? Optionally enter a custom foreign key:

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.